Reviewers: shindig.remailer_gmail.com, mhermanto,

Description:
@see https://issues.apache.org/jira/browse/SHINDIG-1155

Patch #2, provided by Michael Hermanto.

Please review this at http://codereview.appspot.com/107050

Affected files:
  features/src/main/javascript/features/dynamic-height/dynamic-height.js


Index: features/src/main/javascript/features/dynamic-height/dynamic-height.js
===================================================================
--- features/src/main/javascript/features/dynamic-height/dynamic-height.js (revision 803826) +++ features/src/main/javascript/features/dynamic-height/dynamic-height.js (working copy)
@@ -51,23 +51,40 @@
   }

   /**
-   * Calculate the height of the gadget iframe by iterating through the
-   * elements in the gadget body for Webkit.
-   * @returns {int} the height of the gadget.
+   * For Webkit-based browsers, recursively find the maximum y-coordinate
+   * of all elements in subtree rooted at rootNode (except document.body),
+   * accounting each element's height, padding, margin and border.
+   * @param {elem} rootNode node of subtree to find maximum y-coord from.
+   * @param {int} maxSoFar the maximum y-coord found so far.
+   * @returns {int} the greater between maximum y-coord of subtree
+   *                and maxSoFar.
    */
-  function getHeightForWebkit() {
+  function getHeightForWebkitForSubtree(rootNode, maxSoFar) {
     var result = 0;
-    var children = document.body.childNodes;
+    if (rootNode !== document.body
+        && typeof rootNode.offsetTop !== 'undefined'
+        && typeof rootNode.scrollHeight !== 'undefined') {
+      result = rootNode.offsetTop + rootNode.scrollHeight +
+          parseIntFromElemPxAttribute(rootNode, "margin-bottom");
+    }
+    var children = rootNode.childNodes;
     for (var i = 0; i < children.length; i++) {
-      if (typeof children[i].offsetTop !== 'undefined' &&
-          typeof children[i].scrollHeight !== 'undefined') {
- // scrollHeight already accounts for border-bottom and padding-bottom.
-        var bottom = children[i].offsetTop + children[i].scrollHeight
-            + parseIntFromElemPxAttribute(children[i], "margin-bottom");
-        result = Math.max(result, bottom);
-      }
+      result = getHeightForWebkitForSubtree(children[i], result);
     }
-    // Add border, padding and margin of the containing body.
+    return Math.max(result, maxSoFar);
+  }
+
+  /**
+ * For Webkit-based browsers, calculate the height of the gadget iframe by
+   * iterating through the all elements in the gadget. It is not sufficient
+   * to only account <body> children elements, because CSS style position
+ * "float" may place a child element outside of the containig parent element.
+   * Not counting "float" elements may lead to undercounting.
+   *
+   * @returns {int} the height of the gadget.
+   */
+  function getHeightForWebkit() {
+    var result = getHeightForWebkitForSubtree(document.body, 0);
     return result
         + parseIntFromElemPxAttribute(document.body, "border-bottom")
         + parseIntFromElemPxAttribute(document.body, "margin-bottom")


Reply via email to