Bug 677673 - Fix position of bookmarks menu on tablets. r=mfinkle
authorWes Johnston <wjohnston@mozilla.com>
Fri, 02 Sep 2011 10:16:48 -0700
changeset 76477 9ca2aaaae7bfeffe3d15043f318ec548799c73bb
parent 76476 1165ef56bec876518622d0a70df144b532390a20
child 76478 b1063cb1f393689bab95d878265c0f0f8e1c1fad
push id21112
push usermak77@bonardo.net
push dateSat, 03 Sep 2011 09:50:21 +0000
treeherdermozilla-central@e1d7cac1fa83 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmfinkle
bugs677673
milestone9.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 677673 - Fix position of bookmarks menu on tablets. r=mfinkle
mobile/chrome/content/AppMenu.js
mobile/chrome/content/BookmarkPopup.js
mobile/chrome/content/bindings/arrowbox.xml
mobile/chrome/content/common-ui.js
mobile/themes/core/honeycomb/platform.css
--- a/mobile/chrome/content/AppMenu.js
+++ b/mobile/chrome/content/AppMenu.js
@@ -53,24 +53,18 @@ var AppMenu = {
         label.setAttribute("value", child.label);
         item.appendChild(label);
 
         if (item.classList.contains("appmenu-pageaction"))
           siteCommandsBox.appendChild(item);
         else
           listbox.appendChild(item);
       }
-
-      this.popup.top = menuButton.getBoundingClientRect().bottom;
-
-      let chromeReg = Cc["@mozilla.org/chrome/chrome-registry;1"].getService(Ci.nsIXULChromeRegistry);
-      this.popup.setAttribute(chromeReg.isLocaleRTL("global") ? "left" : "right", this.offset);
-
       this.popup.hidden = false;
-      this.popup.anchorTo(menuButton);
+      this.popup.anchorTo(menuButton, "after_end");
 
       BrowserUI.lockToolbar();
       BrowserUI.pushPopup(this, [this.popup, menuButton]);
     } else {
       let shown = 0;
       let lastShown = null;
       this.overflowMenu = [];
       let childrenCount = this.panel.childElementCount;
--- a/mobile/chrome/content/BookmarkPopup.js
+++ b/mobile/chrome/content/BookmarkPopup.js
@@ -14,30 +14,28 @@ var BookmarkPopup = {
   hide : function hide() {
     this.box.hidden = true;
     BrowserUI.popPopup(this);
   },
 
   show : function show() {
     // Set the box position.
     let button = document.getElementById("tool-star");
+    let anchorPosition = "";
     if (getComputedStyle(button).visibility == "visible") {
       let [tabsSidebar, controlsSidebar] = [Elements.tabs.getBoundingClientRect(), Elements.controls.getBoundingClientRect()];
       this.box.setAttribute(tabsSidebar.left < controlsSidebar.left ? "right" : "left", controlsSidebar.width - this.box.offset);
       this.box.top = button.getBoundingClientRect().top - this.box.offset;
     } else {
       button = document.getElementById("tool-star2");
-      this.box.top = button.getBoundingClientRect().bottom - this.box.offset;
-
-      let chromeReg = Cc["@mozilla.org/chrome/chrome-registry;1"].getService(Ci.nsIXULChromeRegistry);
-      this.box.setAttribute(chromeReg.isLocaleRTL("global") ? "left" : "right", this.box.offset);
+      anchorPosition = "after_start";
     }
 
     this.box.hidden = false;
-    this.box.anchorTo(button);
+    this.box.anchorTo(button, anchorPosition);
 
     // include the star button here, so that click-to-dismiss works as expected
     BrowserUI.pushPopup(this, [this.box, button]);
   },
 
   toggle : function toggle() {
     if (this.box.hidden)
       this.show();
--- a/mobile/chrome/content/bindings/arrowbox.xml
+++ b/mobile/chrome/content/bindings/arrowbox.xml
@@ -144,33 +144,105 @@
               arrow.hidden = hideArrow;
               arrow.setAttribute("side", anchorClass);
             ]]>
          </body>
       </method>
       <field name="anchorNode">null</field>
       <method name="anchorTo">
          <parameter name="aAnchorNode"/>
+         <parameter name="aPosition"/>
          <body>
             <![CDATA[
               if (!aAnchorNode) {
                 this._updateArrow(null, null, 0, 0);
                 return;
               }
 
               this.anchorNode = aAnchorNode;
 
               let anchorRect = aAnchorNode.getBoundingClientRect();
-              let popupRect = this.firstChild.getBoundingClientRect();
+              let popupRect = new Rect(0,0,0,0);
+              for (let i = 0; i < this.childNodes.length; i++) {
+                popupRect.expandToContain(Rect.fromRect(this.childNodes[i].getBoundingClientRect()));
+              }
               let offset = this.offset;
+              let horizPos = 0;
+              let vertPos = 0;
+
+              if (aPosition) {
+                let chromeReg = Cc["@mozilla.org/chrome/chrome-registry;1"].getService(Ci.nsIXULChromeRegistry);
+                let isRtl = chromeReg.isLocaleRTL("global");
+                let left = 0;
+                let top = 0;
 
-              let horizPos = (Math.round(popupRect.right) <= Math.round(anchorRect.left + offset)) ? -1 :
-                             (Math.round(popupRect.left) >= Math.round(anchorRect.right - offset)) ? 1 : 0;
-              let vertPos = (Math.round(popupRect.bottom) <= Math.round(anchorRect.top + offset)) ? -1 :
-                            (Math.round(popupRect.top) >= Math.round(anchorRect.bottom - offset)) ? 1 : 0;
+                switch (aPosition) {
+                  case "before_start":
+                    left = isRtl ? anchorRect.right - popupRect.width : anchorRect.left;
+                    top = anchorRect.top + offset - popupRect.height;
+                    vertPos = -1;
+                    break;
+                  case "before_end":
+                    left = isRtl ? anchorRect.left : anchorRect.right - popupRect.width;
+                    top = anchorRect.top + offset - popupRect.height;
+                    vertPos = -1;
+                    break;
+                  case "after_start":
+                    left = isRtl ? anchorRect.right - popupRect.width : anchorRect.left;
+                    top = anchorRect.bottom - offset;
+                    vertPos = 1;
+                    break;
+                  case "after_end":
+                    left = isRtl ? anchorRect.left : anchorRect.right - popupRect.width;
+                    top = anchorRect.bottom - offset;
+                    vertPos = 1;
+                    break;
+                  case "start_before":
+                    left = isRtl ? anchorRect.right : anchorRect.left - popupRect.width - offset;
+                    top = anchorRect.top;
+                    horizPos = -1;
+                    break;
+                  case "start_after":
+                    left = isRtl ? anchorRect.right : anchorRect.left - popupRect.width - offset;
+                    top = anchorRect.bottom - popupRect.height;
+                    horizPos = -1;
+                    break;
+                  case "end_before":
+                    left = isRtl ? anchorRect.left - popupRect.width - offset : anchorRect.right;
+                    top = anchorRect.top;
+                    horizPos = 1;
+                    break;
+                  case "end_after":
+                    left = isRtl ? anchorRect.left - popupRect.width - offset : anchorRect.right;
+                    top = anchorRect.bottom - popupRect.height;
+                    horizPos = 1;
+                    break;
+                  case "overlap":
+                    left = isRtl ? anchorRect.right - popupRect.width + offset : anchorRect.left + offset ;
+                    top = anchorRect.top + offset ;
+                    break;
+                }
+                if (top == 0) top = 1;
+                if (left == 0) left = 1;
+
+                if (left + popupRect.width > window.innerWidth)
+                  left = window.innerWidth - popupRect.width;
+                else if (left < 0)
+                  left = 1;
+
+                popupRect.left = left;
+                this.setAttribute("left", left);
+                popupRect.top = top;
+                this.setAttribute("top", top);
+              } else {
+                horizPos = (Math.round(popupRect.right) <= Math.round(anchorRect.left + offset)) ? -1 :
+                               (Math.round(popupRect.left) >= Math.round(anchorRect.right - offset)) ? 1 : 0;
+                vertPos = (Math.round(popupRect.bottom) <= Math.round(anchorRect.top + offset)) ? -1 :
+                              (Math.round(popupRect.top) >= Math.round(anchorRect.bottom - offset)) ? 1 : 0;
+              }
 
               this._updateArrow(popupRect, anchorRect, horizPos, vertPos);
             ]]>
          </body>
       </method>
 
       <method name="pointLeftAt">
          <parameter name="targetNode"/>
--- a/mobile/chrome/content/common-ui.js
+++ b/mobile/chrome/content/common-ui.js
@@ -82,33 +82,22 @@ var BrowserSearch = {
       button.setAttribute("pack", "start");
       button.setAttribute("image", aEngine.iconURI ? aEngine.iconURI.spec : "");
       list.appendChild(button);
     });
 
     popup.hidden = false;
     popup.top = BrowserUI.toolbarH - popup.offset;
     let searchButton = document.getElementById("tool-search");
-    if (Util.isTablet()) {
-      let width = list.getBoundingClientRect().width;
-      let searchButtonRect = searchButton.getBoundingClientRect();
-      let left = searchButtonRect.left;
-      if (Util.localeDir > 0) {
-        if (left + width > window.innerWidth)
-          left = window.innerWidth - width;
-      } else {
-        left = searchButtonRect.right - width;
-        if (left < 0)
-          left = 0;
-      }
-      popup.left = left;
-    } else if (popup.hasAttribute("left")) {
+    let anchorPosition = "";
+    if (Util.isTablet())
+      anchorPosition = "after_start";
+    else if (popup.hasAttribute("left"))
       popup.removeAttribute("left");
-    }
-    popup.anchorTo(searchButton);
+    popup.anchorTo(searchButton, anchorPosition);
 
     document.getElementById("urlbar-icons").setAttribute("open", "true");
     BrowserUI.pushPopup(this, [popup, this._button]);
   },
 
   hide: function bs_hide() {
     this._popup.hidden = true;
     document.getElementById("urlbar-icons").removeAttribute("open");
--- a/mobile/themes/core/honeycomb/platform.css
+++ b/mobile/themes/core/honeycomb/platform.css
@@ -565,16 +565,20 @@ progressmeter {
 
 /* panels / arrowboxes------------------------------------------------------ */
 arrowbox {
   -moz-appearance: none;
   background: transparent !important;
   border: none;
 }
 
+.panel-arrow {
+  min-height: 18px;
+}
+
 .arrowbox-dark .panel-arrowcontent {
   padding: @padding_normal@; /* core spacing */
 }
 
 dialog,
 .arrowbox-dark .panel-arrowcontent,
 .panel-dark {
   color: @color_text_default@;