[tbb-commits] [torbutton/master] Bug 9268: Fix some resizing corner cases.

mikeperry at torproject.org mikeperry at torproject.org
Fri Jun 27 16:46:27 UTC 2014


commit 32003e19d4a0f41d5c9bdc12fa6db6e6e3836e9a
Author: Georg Koppen <gk at torproject.org>
Date:   Thu Jun 26 15:10:48 2014 +0000

    Bug 9268: Fix some resizing corner cases.
    
    We now take the DPI value into account when calculating the width and
    height of the browser window. Furthermore, using GetAvailRect() helps
    to take care of taskbars that could influence the available height.
    
    At least two corner-corner cases remain:
    
    1) On some Linux machines the height of the titlebar is not included in
       outerHeight(). Thus, we guess with a pretty safe margin.
    2) On some systems retrieving the available height is giving the screen
      height back which could lead to problems if taskbars are available.
    
    Fixing those two problems (and presumably others yet to be reported) is
    out of the scope for this patch.
    
    However, in order to give the user the option to overwrite the
    miscalculation two preferences
    
    extensions.torbutton.window.innerWidth
    extensions.torbutton.window.innerHeigth
    
    are consulted. If they are set their values are used when resizing the
    inner window.
---
 src/chrome/content/torbutton.js |   91 ++++++++++++++++++++++++++++++---------
 1 file changed, 71 insertions(+), 20 deletions(-)

diff --git a/src/chrome/content/torbutton.js b/src/chrome/content/torbutton.js
index 589e7c5..b149a30 100644
--- a/src/chrome/content/torbutton.js
+++ b/src/chrome/content/torbutton.js
@@ -44,6 +44,9 @@ var m_tb_control_pass = null;
 
 var m_tb_orig_BrowserOnAboutPageLoad = null;
 
+var m_tb_domWindowUtils = window.QueryInterface(Ci.nsIInterfaceRequestor).
+                          getInterface(Ci.nsIDOMWindowUtils);
+
 // Bug 1506 P1: This object is only for updating the UI for toggling and style
 var torbutton_window_pref_observer =
 {
@@ -2896,10 +2899,6 @@ var torbutton_resizelistener =
         progress.removeProgressListener(this);
         return;
       }
-      var screenMan = Components.classes["@mozilla.org/gfx/screenmanager;1"].
-        getService(Components.interfaces.nsIScreenManager);
-      var junk = {}, availWidth = {}, availHeight = {};
-      screenMan.primaryScreen.GetRect(junk, junk, availWidth, availHeight);
 
       // We need to set the inner width to an initial value because it has none
       // at this point... Choosing "300" as this works even on Windows
@@ -2907,26 +2906,78 @@ var torbutton_resizelistener =
       win.innerWidth = 300;
       win.innerHeight = 300;
 
-      torbutton_log(3, "About to resize new window: " + window.outerWidth +
-        "x" + window.outerHeight + " inner: " + win.innerWidth + "x" + win.
-        innerHeight + " in state " + window.windowState + " Have " +
-        availWidth.value + "x" + availHeight.value);
+      var screenMan = Components.classes["@mozilla.org/gfx/screenmanager;1"].
+        getService(Components.interfaces.nsIScreenManager);
+      var junk = {}, availWidth = {}, availHeight = {};
+      screenMan.primaryScreen.GetAvailRect(junk, junk, availWidth, availHeight);
+
+      torbutton_log(3, "About to resize window: " +
+                    window.outerWidth + "x" + window.outerHeight +
+                    " inner: " + win.innerWidth + "x" + win.innerHeight +
+                    " in state " + window.windowState +
+                    " Available: " + availWidth.value + "x" +
+                    availHeight.value);
+
+      var diff_height = window.outerHeight - win.innerHeight;
+      var diff_width = window.outerWidth - win.innerWidth;
+      var delta_fix = 0;
+
+      // The following block tries to cope with funny corner cases where the
+      // title bar is not included in window.outerHeight. What could happen in
+      // this case? Well, assume the difference between window.outerHeight and
+      // win.innerHeight is 39. And lets further assume the available height is
+      // 725x539. If we resize the window in this case we get 600x500 for the
+      // inner window. And the outer window has a height of 539 *plus* the
+      // height of the titlebar (as it occupies some screen space at least
+      // after resizing) which probably leads to parts of the browser being not
+      // visible.
+      if (window.outerHeight == window.innerHeight) {
+          // XXX: Let's assume a reasonable safety margin.
+          // |delta_fix = Math.floor(window.mozInnerScreenY) - window.screenY;|
+          // is not working at this stage of the browser start-up. Although it
+          // would give us slightly better values. But calling it later makes
+          // the resizing visible even on fast computers which is bad for UX.
+          delta_fix = Math.floor(diff_height / 2);
+      }
 
-      var maxHeight = availHeight.value -
-        (window.outerHeight - win.innerHeight) - 51;
-      var maxWidth = availWidth.value - (window.outerWidth - win.innerWidth);
-      torbutton_log(3, "Got max dimensions: " + maxWidth + "x" + maxHeight);
+      // Check the DPI value and take it into acctount later when calculating
+      // the max* values.
+      var dpi = m_tb_domWindowUtils.screenPixelsPerCSSPixel;
+
+      // We can't use screen resolution here as it does not account for e.g.
+      // taskbars. We can't use window.screen.avail* either as it does not
+      // report correct values on some platforms when used at this stage in the
+      // startup process. Therefore, we resort to nsIScreenManager.
+      // XXX: Note though, there are probably still some OS/window manager
+      // configurations where this approach is not working. E.g. on a Debian
+      // with XFCE the available height is the same as the screen height.
+      // This is said to happen as well on Windows with Aero:
+      // https://stackoverflow.com/questions/3044230/
+      // difference-between-screen-availheight-and-window-height
+      var maxHeight = Math.floor(availHeight.value / dpi) -
+                     (diff_height + delta_fix);
+      var maxWidth = Math.floor(availWidth.value / dpi) - diff_width ;
 
       var width;
       var height;
 
-      if (maxWidth > 1000) {
-        width = 1000;
-      } else {
-        width = Math.floor(maxWidth/200.0)*200;
+      // Allow the user to overwrite the Torbutton logic in case it is still
+      // wrong when resizing the window.
+      try {
+        width = m_tb_prefs.getIntPref("extensions.torbutton.window.innerWidth");
+      } catch(e) {
+        if (maxWidth > 1000) {
+          width = 1000;
+        } else {
+          width = Math.floor(maxWidth/200.0)*200;
+        }
       }
 
-      height = Math.floor(maxHeight/100.0)*100;
+      try {
+        height = m_tb_prefs.getIntPref("extensions.torbutton.window.innerHeight");
+      } catch(e) {
+        height = Math.floor(maxHeight/100.0)*100;
+      }
 
       var handler = function() {
         if (window.windowState === 1) {
@@ -2973,8 +3024,8 @@ var torbutton_resizelistener =
       // instead of assignment or resizeTo()
       win.resizeBy(width - win.innerWidth, height - win.innerHeight);
       torbutton_log(3, "Resized new window from: " + win.innerWidth + "x" +
-        win.innerHeight + " to " + width + "x" + height + " in state " +
-        window.windowState);
+                    win.innerHeight + " to " + width + "x" + height +
+                    " in state " + window.windowState);
 
       // Resizing within this progress listener does not always work as overlays
       // of other extensions might still influence the height/width of the
@@ -2992,7 +3043,7 @@ var torbutton_resizelistener =
                 win.innerWidth + " x " + win.innerHeight);
               setTimeout(function() {
                            win.resizeBy(width - win.innerWidth,
-                             height - win.innerHeight);
+                                        height - win.innerHeight);
                            torbutton_log(3, "Mutation observer: Window " +
                              "dimensions are (after resizing again): " + win.
                              innerWidth + " x " + win.innerHeight);





More information about the tbb-commits mailing list