<?xml version="1.0"?>

<!-- ***** BEGIN LICENSE BLOCK *****
   - Version: MPL 1.1/GPL 2.0/LGPL 2.1
   -
   - The contents of this file are subject to the Mozilla Public License Version
   - 1.1 (the "License"); you may not use this file except in compliance with
   - the License. You may obtain a copy of the License at
   - http://www.mozilla.org/MPL/
   -
   - Software distributed under the License is distributed on an "AS IS" basis,
   - WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
   - for the specific language governing rights and limitations under the
   - License.
   -
   - The Original Code is mozilla.org code.
   -
   - The Initial Developer of the Original Code is
   - the mozilla.org SeaMonkey project.
   - Portions created by the Initial Developer are Copyright (C) 2006
   - the Initial Developer. All Rights Reserved.
   -
   - Contributor(s):
   -  Joe Hewitt <hewitt@netscape.com>
   -  Blake Ross <blakeross@telocity.com>
   -  David Hyatt <hyatt@netscape.com>
   -  Peter Annema <jaggernaut@netscape.com>
   -  Aaron Leventhal <aaronl@netscape.com>
   -  John Gaunt <jgaunt@netscape.com>
   -  Brian Ryner <bryner@netscape.com>
   -  Jonas Sicking <sicking@bigfoot.com>
   -  Neil Rashbrook <neil@parkwaycc.co.uk>
   -  Boris Zbarsky <bzbarsky@mit.edu>
   -  Josh Soref <timeless@mac.com>
   -  Jan Varga <varga@netscape.com>
   -  Kyle Yuan <kyle.yuan@sun.com>
   -  <shliang@netscape.com>
   -  Benjamin Smedberg <bsmedberg@covad.net>
   -  Karsten Düsterloh <mnyromyr@tprac.de>
   -
   - Alternatively, the contents of this file may be used under the terms of
   - either the GNU General Public License Version 2 or later (the "GPL"), or
   - the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
   - in which case the provisions of the GPL or the LGPL are applicable instead
   - of those above. If you wish to allow use of your version of this file only
   - under the terms of either the GPL or the LGPL, and not to allow others to
   - use your version of this file under the terms of the MPL, indicate your
   - decision by deleting the provisions above and replace them with the notice
   - and other provisions required by the LGPL or the GPL. If you do not delete
   - the provisions above, a recipient may use your version of this file under
   - the terms of any one of the MPL, the GPL or the LGPL.
   -
   - ***** END LICENSE BLOCK ***** -->

<bindings id="toolbarBindings"
          xmlns="http://www.mozilla.org/xbl"
          xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
          xmlns:xbl="http://www.mozilla.org/xbl">

  <!-- With the move to the new toolkit, SeaMonkey needs to overwrite certain
       bindings if it wants to keep its distinctive likeness. The bindings
       found here reimplement the XPFE toolbar behaviour by providing toolbar
       bindings in in the chrome://communicator/ domain that are based upon the
       new toolkit's toolbar bindings in the chrome://global/ domain.
       The now hidden new toolkit bindings are accessible via a set xpfe="false"
       attribute, though.
    -->

  <binding id="grippytoolbox" extends="chrome://global/content/bindings/toolbar.xml#toolbox">
    <content orient="vertical">
      <xul:vbox flex="1" class="toolbar-internal-box">
        <children/>
      </xul:vbox>
      <xul:hbox tbattr="collapsed-tray-holder" class="collapsed-tray-holder" moz-collapsed="true" xbl:inherits="collapsed=inFullscreen">
        <xul:hbox tbattr="collapsed-tray" class="collapsed-tray"/>
        <xul:spacer flex="1" class="collapsed-tray-spacer"/>
      </xul:hbox>
    </content>
    <implementation>
      <field name="palette">
        this.getElementsByTagName("toolbarpalette").item(0);
      </field>

      <constructor>
        <![CDATA[
          var set = this.toolbarset;
          if (!set)
            return;
          var toolbars = this.getElementsByAttribute("customindex", "*");
          for (let i = 0; i < toolbars.length; ++i) {
            let bar = toolbars[i];
            let name = bar.getAttribute("toolbarname").replace(" ", "_");
            if (name) {
              let attrs = ["mode", "iconsize", "labelalign", "hidden",
                           "collapsed", "moz-collapsed"];
              for (let j = 0; j < attrs.length; j++) {
                let attr = set.getAttribute(name + attrs[j]);
                if (attr)
                  bar.setAttribute(attrs[j], attr);
              }
              bar.setAttribute("grippytooltiptext", name);
            }
          }
        ]]>
      </constructor>

      <method name="collapseToolbar">
        <parameter name="toolbar"/>
        <body>
        <![CDATA[
          try {
            this.createCollapsedGrippy(toolbar);
            toolbar.setAttribute("collapsed", "true");
            document.persist(toolbar.id, "collapsed");
            toolbar.removeAttribute("moz-collapsed");
            document.persist(toolbar.id, "moz-collapsed");
            if (toolbar.hasAttribute("customindex"))
              this.persistCustomCollapse(toolbar, "true");
          }
          catch(e) {
          }
        ]]>
        </body>
      </method>

      <method name="expandToolbar">
        <parameter name="aGrippyID"/>
        <body>
        <![CDATA[
          var idString = aGrippyID.substring("moz_tb_collapsed_".length, aGrippyID.length);
          var toolbar = document.getElementById(idString);
          toolbar.setAttribute("collapsed", "false");
          var collapsedTray = document.getAnonymousElementByAttribute(this, "tbattr", "collapsed-tray");
          var collapsedToolbar = document.getElementById("moz_tb_collapsed_" + toolbar.id);
          collapsedTray.removeChild(collapsedToolbar);
          if (!collapsedTray.hasChildNodes())
            document.getAnonymousElementByAttribute(this, "tbattr", "collapsed-tray-holder").setAttribute("moz-collapsed", "true");
          document.persist(toolbar.id, "collapsed");
          if (toolbar.hasAttribute("customindex"))
            this.persistCustomCollapse(toolbar, "false");
        ]]>
        </body>
      </method>

      <method name="createCollapsedGrippy">
        <parameter name="aToolbar"/>
        <body>
        <![CDATA[
          const XUL_NS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
          var existingGrippy = document.getAnonymousElementByAttribute(this, "id", "moz_tb_collapsed_" + aToolbar.id);
          if (!existingGrippy) {
            var grippy = document.getAnonymousElementByAttribute(aToolbar, "tbattr", "toolbar-grippy");
            var boxObject = grippy.boxObject.QueryInterface(Components.interfaces.nsIBoxObject);
            var collapsedGrippy = document.createElementNS(XUL_NS, "toolbargrippy");
            if (collapsedGrippy) {
              var width = boxObject.height > 20 ? boxObject.height : 23;
              var height = boxObject.width > 10 ? boxObject.width : 12;
              var styleString = "width: " + width + "px; height: " + height + "px;";
              collapsedGrippy.setAttribute("style", styleString);
              collapsedGrippy.setAttribute("tooltiptext", aToolbar.getAttribute("grippytooltiptext"));
              collapsedGrippy.setAttribute("id", "moz_tb_collapsed_" + aToolbar.id);
              collapsedGrippy.setAttribute("moz_grippy_collapsed", "true");
              collapsedGrippy.setAttribute("tbgrippy-collapsed", "true");
              var collapsedTrayHolder = document.getAnonymousElementByAttribute(this, "tbattr", "collapsed-tray-holder");
              if (collapsedTrayHolder.getAttribute("moz-collapsed") == "true")
                collapsedTrayHolder.removeAttribute("moz-collapsed");
              document.getAnonymousElementByAttribute(this, "tbattr", "collapsed-tray").appendChild(collapsedGrippy);
            }
          }
        ]]>
        </body>
      </method>

      <method name="persistCustomCollapse">
        <parameter name="toolbar"/>
        <parameter name="collapsed"/>
        <body>
        <![CDATA[
          var attr = toolbar.getAttribute("toolbarname").replace(" ", "_") + "collapsed";
          this.toolbarset.setAttribute(attr, collapsed);
          document.persist(this.toolbarset.id, attr);
          var attr = toolbar.getAttribute("toolbarname").replace(" ", "_") + "moz-collapsed";
          this.toolbarset.removeAttribute(attr);
          document.persist(this.toolbarset.id, attr);
        ]]>
        </body>
      </method>
    </implementation>
  </binding>

  <binding id="grippytoolbar" extends="chrome://global/content/bindings/toolbar.xml#toolbar">
    <content>
      <xul:hbox flex="1" class="toolbar-box box-inherit">
        <xul:toolbargrippy xbl:inherits="last-toolbar,hidden=grippyhidden,collapsed=inFullscreen"
                           tbattr="toolbar-grippy"
                           class="toolbar-grippy"/>
        <xul:hbox flex="1" class="toolbar-holder box-inherit"
                  xbl:inherits="collapsed,last-toolbar,orient,align,pack">
          <children/>
        </xul:hbox>
      </xul:hbox>
    </content>

    <implementation>
      <constructor>
        <![CDATA[
          if (this.getAttribute("moz-collapsed") == "true" &&
              this.parentNode.localName == "toolbox")
            this.parentNode.collapseToolbar(this);
          else if (this.getAttribute("collapsed") == "true" &&
                   this.parentNode.localName == "toolbox")
            this.parentNode.createCollapsedGrippy(this);
        ]]>
      </constructor>
    </implementation>
  </binding>

  <binding id="grippytoolbar-primary" extends="chrome://communicator/content/bindings/toolbar.xml#grippytoolbar">
    <implementation implements="nsIObserver">
      <constructor>
        <![CDATA[
          this.prefs.addObserver(this.domain, this, false);
          if (this.prefs.getIntPref(this.domain) != 2)
            this.observe(this.prefs, "nsPref:changed", this.domain);
        ]]>
      </constructor>

      <destructor>
        this.prefs.removeObserver(this.domain, this);
      </destructor>

      <field name="domain" readonly="true">
        "browser.chrome.toolbar_style"
      </field>

      <field name="prefs" readonly="true">
        Components.classes["@mozilla.org/preferences-service;1"]
                  .getService(Components.interfaces.nsIPrefService).getBranch(null)
                  .QueryInterface(Components.interfaces.nsIPrefBranch2)
      </field>

      <method name="observe">
        <parameter name="subject"/>
        <parameter name="topic"/>
        <parameter name="name"/>
        <body>
          <![CDATA[
            if (topic == "nsPref:changed" && name == this.domain) {
              const styles = ["icons", "text", null];
              const style = styles[this.prefs.getIntPref(name)];
              this.parentNode.setAttribute("mode", style); // toolbox
              if (!this.hasAttribute("customizable") ||
                  !this.hasAttribute("ignoremodepref"))
                this.setAttribute("mode", style);
            }
          ]]>
        </body>
      </method>
    </implementation>
  </binding>

  <binding id="grippytoolbar-drag"
           extends="chrome://communicator/content/bindings/toolbar.xml#grippytoolbar">
    <implementation>
      <field name="_dragBindingAlive">true</field>
      <constructor>
        <![CDATA[
          if (!this._draggableStarted) {
            this._draggableStarted = true;
            try {
              let tmp = {};
              Components.utils.import("resource://gre/modules/WindowDraggingUtils.jsm", tmp);
              let draggableThis = new tmp.WindowDraggingElement(this, window);
              draggableThis.mouseDownCheck = function(e) {
                // Don't move while customizing.
                return this._dragBindingAlive &&
                       this.getAttribute("customizing") != "true";
              }
            } catch (e) {}
          }
        ]]>
      </constructor>
    </implementation>
  </binding>

  <binding id="grippytoolbar-primary-drag"
           extends="chrome://communicator/content/bindings/toolbar.xml#grippytoolbar-primary">
    <implementation>
    <field name="_dragBindingAlive">true</field>
      <constructor>
        <![CDATA[
          if (!this._draggableStarted) {
            this._draggableStarted = true;
            try {
              let tmp = {};
              Components.utils.import("resource://gre/modules/WindowDraggingUtils.jsm", tmp);
              let draggableThis = new tmp.WindowDraggingElement(this, window);
              draggableThis.mouseDownCheck = function(e) {
                // Don't move while customizing.
                return this._dragBindingAlive &&
                       this.getAttribute("customizing") != "true";
              }
            } catch (e) {}
          }
        ]]>
      </constructor>
    </implementation>
  </binding>

  <binding id="grippytoolbar-menubar"
           extends="chrome://communicator/content/bindings/toolbar.xml#grippytoolbar"
           display="xul:menubar"/>

  <binding id="grippymenubar" extends="chrome://global/content/bindings/toolbar.xml#menubar">
    <content>
      <xul:hbox flex="1" class="toolbar-box">
        <xul:toolbargrippy xbl:inherits="last-toolbar,hidden=grippyhidden"
                           tbattr="toolbar-grippy" class="toolbar-grippy"/>
        <xul:hbox flex="1" class="toolbar-holder" xbl:inherits="collapsed,last-toolbar">
          <children/>
        </xul:hbox>
      </xul:hbox>
    </content>
    <implementation>
      <constructor>
        <![CDATA[
          if (this.getAttribute("moz-collapsed") == "true" &&
              this.parentNode.localName == "toolbox")
            this.parentNode.collapseToolbar(this);
          else if (this.getAttribute("collapsed") == "true" &&
                   this.parentNode.localName == "toolbox")
            this.parentNode.createCollapsedGrippy(this);
        ]]>
      </constructor>
    </implementation>
  </binding>

  <binding id="toolbargrippy" display="xul:button"
           extends="chrome://global/content/bindings/toolbar.xml#toolbar-base">
    <content>
      <xul:image class="toolbargrippy-arrow"/>
      <xul:spacer class="toolbargrippy-texture" flex="1"/>
    </content>

    <implementation>
      <property name="collapsed">
        <getter>
          return this.hasAttribute("moz_grippy_collapsed");
        </getter>
        <setter>
          if (val)
            this.setAttribute("moz_grippy_collapsed", "true");
          else
            this.removeAttribute("moz_grippy_collapsed");
          return val;
        </setter>
      </property>

      <method name="returnNode">
        <parameter name="aNodeA"/>
        <parameter name="aNodeB"/>
        <body>
        <![CDATA[
          var node = this.parentNode;
          while (node && node.localName != "window" &&
                 (node.localName != aNodeA && (node.localName != aNodeB)))  {
            node = node.parentNode;
          }
          return node;
        ]]>
        </body>
      </method>

      <method name="grippyTriggered">
        <body>
        <![CDATA[
          var toolbox = this.returnNode("toolbox");
          var toolbar = this.returnNode("toolbar", "menubar");
          if (this.collapsed)
            toolbox.expandToolbar(this.id);
          else
            toolbox.collapseToolbar(toolbar);
        ]]>
        </body>
      </method>
    </implementation>

    <handlers>
      <handler event="command">
      <![CDATA[
        this.grippyTriggered();
      ]]>
      </handler>
    </handlers>
  </binding>

</bindings>

