Bug 726817 - Use nsIFrameLoaderOwner.clampScrollPosition to fix clip on zoom.
authorChris Lord <chrislord.net@gmail.com>
Fri, 17 Feb 2012 23:44:47 +0000
changeset 92494 cf7c1f3d4c7f689787ed3ca71ebe2be9c88c13a7
parent 92493 bf93d4ab5d9976d00ac17a6fa0d6b08a38a6c2aa
child 92495 0e7445af29d1b8ddd7bec875228b07799ab6419c
push idunknown
push userunknown
push dateunknown
bugs726817
milestone13.0a1
Bug 726817 - Use nsIFrameLoaderOwner.clampScrollPosition to fix clip on zoom. Zooming in caused the right and bottom edges of the page to be clipped. This was because we would try to scroll to coordinates that, untransformed, would be invalid. The document has no knowledge of the zoom, and so the scroll position needs to be forced somehow. Java compositor accomplished this using a CSS translation transformation, this accomplishes it by turning off scroll position clamping (a technique that the Java compositor should also employ, if the patch this relies on passes review).
mobile/android/chrome/content/browser.js
--- a/mobile/android/chrome/content/browser.js
+++ b/mobile/android/chrome/content/browser.js
@@ -1482,16 +1482,17 @@ Tab.prototype = {
     this.browser.style.height = gScreenHeight + "px";
     this.vbox.appendChild(this.browser);
 
     this.browser.stop();
 
     let frameLoader = this.browser.QueryInterface(Ci.nsIFrameLoaderOwner).frameLoader;
     if (kUsingGLLayers) {
         frameLoader.renderMode = Ci.nsIFrameLoader.RENDER_MODE_ASYNC_SCROLL;
+        frameLoader.clampScrollPosition = false;
     } else {
         // Turn off clipping so we can buffer areas outside of the browser element.
         frameLoader.clipSubdocument = false;
     }
 
     this.id = ++gTabIDFactory;
 
     let message = {
@@ -1599,38 +1600,29 @@ Tab.prototype = {
     aViewport.y /= aViewport.zoom;
 
     // Set scroll position
     let win = this.browser.contentWindow;
     win.scrollTo(aViewport.x, aViewport.y);
     this.userScrollPos.x = win.scrollX;
     this.userScrollPos.y = win.scrollY;
 
-    // If we've been asked to over-scroll, do it via the transformation
-    // and store it separately to the viewport.
-    let excessX = aViewport.x - win.scrollX;
-    let excessY = aViewport.y - win.scrollY;
-
     this._viewport.width = gScreenWidth = aViewport.width;
     this._viewport.height = gScreenHeight = aViewport.height;
     dump("### gScreenWidth = " + gScreenWidth + "\n");
 
     let zoom = aViewport.zoom;
     let cwu = window.top.QueryInterface(Ci.nsIInterfaceRequestor)
                          .getInterface(Ci.nsIDOMWindowUtils);
 
-    if ((aViewport.offsetX != this._viewport.offsetX) ||
-        (excessX != this.viewportExcess.x)) {
+    if (aViewport.offsetX != this._viewport.offsetX) {
       this._viewport.offsetX = aViewport.offsetX;
-      this.viewportExcess.x = excessX;
     }
-    if ((aViewport.offsetY != this._viewport.offsetY) ||
-        (excessY != this.viewportExcess.y)) {
+    if (aViewport.offsetY != this._viewport.offsetY) {
       this._viewport.offsetY = aViewport.offsetY;
-      this.viewportExcess.y = excessY;
     }
     if (Math.abs(zoom - this._viewport.zoom) >= 1e-6) {
       this._viewport.zoom = zoom;
       cwu.setResolution(zoom, zoom);
     }
 
     cwu.setDisplayPortForElement(-kBufferAmount / zoom, -kBufferAmount / zoom,
                                  (gScreenWidth + kBufferAmount * 2) / zoom,