customizetoolbar.js

来自「现在很火的邮件客户端软件thunderbird的源码」· JavaScript 代码 · 共 960 行 · 第 1/2 页

JS
960
字号
# ***** 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 Communicator client code, released# March 31, 1998.## The Initial Developer of the Original Code is# David Hyatt.# Portions created by the Initial Developer are Copyright (C) 2002# the Initial Developer. All Rights Reserved.## Contributor(s):#   David Hyatt (hyatt@apple.com)#   Blake Ross (blaker@netscape.com)#   Joe Hewitt (hewitt@netscape.com)## 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 GPL or the LGPL. 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 *****const kRowMax = 4;const kWindowWidth = 600;const kWindowHeight = 400;const kAnimateIncrement = 50;const kAnimateSteps = kWindowHeight / kAnimateIncrement - 1;const kVSizeSlop = 5;var gToolboxDocument = null;var gToolbox = null;var gCurrentDragOverItem = null;var gToolboxChanged = false;var gPreviousMode = null;var gPreviousIconSize = null;function onLoad(){  gToolbox = window.arguments[0];  gToolboxDocument = gToolbox.ownerDocument;    gToolbox.addEventListener("draggesture", onToolbarDragGesture, false);  gToolbox.addEventListener("dragover", onToolbarDragOver, false);  gToolbox.addEventListener("dragexit", onToolbarDragExit, false);  gToolbox.addEventListener("dragdrop", onToolbarDragDrop, false);  repositionDialog();  initDialog();}function onUnload(aEvent){  removeToolboxListeners();  unwrapToolbarItems(true);  persistCurrentSets();    notifyParentComplete();}function onCancel(){  // restore the saved toolbarset for each customizeable toolbar  unwrapToolbarItems(false);  var toolbar = gToolbox.firstChild;  while (toolbar) {    if (isCustomizableToolbar(toolbar)) {      if (!toolbar.hasAttribute("customindex")) {        var previousset = toolbar.getAttribute("previousset");        if (previousset)        {          toolbar.currentSet = previousset;        }      }    }    toolbar = toolbar.nextSibling;  }  // restore the previous mode and iconsize  updateIconSize(gPreviousIconSize == "small");  updateToolbarMode(gPreviousMode);  repositionDialog();  gToolboxChanged = true;  return onAccept(); // we restored the default toolbar, act like a normal accept event now}function onAccept(aEvent){  document.getElementById("main-box").collapsed = true;  window.close();}function initDialog(){  document.getElementById("main-box").collapsed = false;    gPreviousMode = gToolbox.getAttribute("mode");  document.getElementById("modelist").value = gPreviousMode;  gPreviousIconSize = gToolbox.getAttribute("iconsize");  var smallIconsCheckbox = document.getElementById("smallicons");  if (gPreviousMode == "text")    smallIconsCheckbox.disabled = true;  else    smallIconsCheckbox.checked = gPreviousIconSize == "small";  // Build up the palette of other items.  buildPalette();  // Wrap all the items on the toolbar in toolbarpaletteitems.  wrapToolbarItems(true);}function repositionDialog(){  // Position the dialog touching the bottom of the toolbox and centered with   // it. We must resize the window smaller first so that it is positioned   // properly.   var screenX = gToolbox.boxObject.screenX + ((gToolbox.boxObject.width - kWindowWidth) / 2);  var screenY = gToolbox.boxObject.screenY + gToolbox.boxObject.height;  var newHeight = kWindowHeight;  if (newHeight >= screen.availHeight - screenY - kVSizeSlop) {    newHeight = screen.availHeight - screenY - kVSizeSlop;  }  window.resizeTo(kWindowWidth, newHeight);  window.moveTo(screenX, screenY);}function removeToolboxListeners(){  gToolbox.removeEventListener("draggesture", onToolbarDragGesture, false);  gToolbox.removeEventListener("dragover", onToolbarDragOver, false);  gToolbox.removeEventListener("dragexit", onToolbarDragExit, false);  gToolbox.removeEventListener("dragdrop", onToolbarDragDrop, false);}/** * Invoke a callback on the toolbox to notify it that the dialog is done * and going away. */function notifyParentComplete(){  if ("customizeDone" in gToolbox)    gToolbox.customizeDone(gToolboxChanged);}function getToolbarAt(i){  return gToolbox.childNodes[i];}/** * Persist the current set of buttons in all customizable toolbars to * localstore. */function persistCurrentSets(){  if (!gToolboxChanged)    return;  var customCount = 0;  for (var i = 0; i < gToolbox.childNodes.length; ++i) {    // Look for customizable toolbars that need to be persisted.    var toolbar = getToolbarAt(i);    if (isCustomizableToolbar(toolbar)) {      // Calculate currentset and store it in the attribute.      var currentSet = toolbar.currentSet;      toolbar.setAttribute("currentset", currentSet);            var customIndex = toolbar.hasAttribute("customindex");      if (customIndex) {        if (!toolbar.firstChild) {          // Remove custom toolbars whose contents have been removed.          gToolbox.removeChild(toolbar);          --i;        } else {          // Persist custom toolbar info on the <toolbarset/>          gToolbox.toolbarset.setAttribute("toolbar"+(++customCount),                                           toolbar.toolbarName + ":" + currentSet);          gToolboxDocument.persist(gToolbox.toolbarset.id, "toolbar"+customCount);        }      }      if (!customIndex) {        // Persist the currentset attribute directly on hardcoded toolbars.        gToolboxDocument.persist(toolbar.id, "currentset");      }    }  }    // Remove toolbarX attributes for removed toolbars.  while (gToolbox.toolbarset.hasAttribute("toolbar"+(++customCount))) {    gToolbox.toolbarset.removeAttribute("toolbar"+customCount);    gToolboxDocument.persist(gToolbox.toolbarset.id, "toolbar"+customCount);  }}/** * Wraps all items in all customizable toolbars in a toolbox. */function wrapToolbarItems(aStorePreviousSet){  for (var i = 0; i < gToolbox.childNodes.length; ++i) {    var toolbar = getToolbarAt(i);    if (isCustomizableToolbar(toolbar)) {      if (aStorePreviousSet)        toolbar.setAttribute('previousset', toolbar.currentSet);      for (var k = 0; k < toolbar.childNodes.length; ++k) {        var item = toolbar.childNodes[k];        if (isToolbarItem(item)) {          var nextSibling = item.nextSibling;                    var wrapper = wrapToolbarItem(item);               if (nextSibling)            toolbar.insertBefore(wrapper, nextSibling);          else            toolbar.appendChild(wrapper);        }      }    }  }}/** * Unwraps all items in all customizable toolbars in a toolbox. */ function unwrapToolbarItems(aRemovePreviousSet){  for (var i = 0; i < gToolbox.childNodes.length; ++i) {    var toolbar = getToolbarAt(i);    if (isCustomizableToolbar(toolbar)) {      if (aRemovePreviousSet)        toolbar.removeAttribute('previousset');      for (var k = 0; k < toolbar.childNodes.length; ++k) {        var paletteItem = toolbar.childNodes[k];        var toolbarItem = paletteItem.firstChild;        if (toolbarItem && isToolbarItem(toolbarItem)) {          var nextSibling = paletteItem.nextSibling;          if (paletteItem.hasAttribute("itemcommand"))            toolbarItem.setAttribute("command", paletteItem.getAttribute("itemcommand"));          if (paletteItem.hasAttribute("itemobserves"))            toolbarItem.setAttribute("observes", paletteItem.getAttribute("itemobserves"));          paletteItem.removeChild(toolbarItem);           paletteItem.parentNode.removeChild(paletteItem);          if (nextSibling)            toolbar.insertBefore(toolbarItem, nextSibling);          else            toolbar.appendChild(toolbarItem);        }      }    }  }}/** * Creates a wrapper that can be used to contain a toolbaritem and prevent * it from receiving UI events. */function createWrapper(aId){  var wrapper = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                         "toolbarpaletteitem");  wrapper.id = "wrapper-"+aId;    return wrapper;}/** * Wraps an item that has been cloned from a template and adds * it to the end of a row in the palette. */function wrapPaletteItem(aPaletteItem, aCurrentRow, aSpacer){  var wrapper = createWrapper(aPaletteItem.id);  wrapper.setAttribute("flex", 1);  wrapper.setAttribute("align", "center");  wrapper.setAttribute("pack", "center");  wrapper.setAttribute("minheight", "0");  wrapper.setAttribute("minwidth", "0");  wrapper.appendChild(aPaletteItem);    // XXX We need to call this AFTER the palette item has been appended  // to the wrapper or else we crash dropping certain buttons on the   // palette due to removal of the command and disabled attributes - JRH  cleanUpItemForPalette(aPaletteItem, wrapper);  if (aSpacer)    aCurrentRow.insertBefore(wrapper, aSpacer);  else    aCurrentRow.appendChild(wrapper);}/** * Wraps an item that is currently on a toolbar and replaces the item * with the wrapper. This is not used when dropping items from the palette, * only when first starting the dialog and wrapping everything on the toolbars. */function wrapToolbarItem(aToolbarItem){  var wrapper = createWrapper(aToolbarItem.id);    cleanupItemForToolbar(aToolbarItem, wrapper);  wrapper.flex = aToolbarItem.flex;  if (aToolbarItem.parentNode)    aToolbarItem.parentNode.removeChild(aToolbarItem);    wrapper.appendChild(aToolbarItem);    return wrapper;}/** * Get the list of ids for the current set of items on each toolbar. */function getCurrentItemIds(){  var currentItems = {};  for (var i = 0; i < gToolbox.childNodes.length; ++i) {    var toolbar = getToolbarAt(i);    if (isCustomizableToolbar(toolbar)) {      var child = toolbar.firstChild;      while (child) {        if (isToolbarItem(child))          currentItems[child.id] = 1;        child = child.nextSibling;      }    }  }  return currentItems;}/** * Builds the palette of draggable items that are not yet in a toolbar. */function buildPalette(){  // Empty the palette first.  var paletteBox = document.getElementById("palette-box");  while (paletteBox.lastChild)    paletteBox.removeChild(paletteBox.lastChild);  var currentRow = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                            "hbox");  currentRow.setAttribute("class", "paletteRow");  // Add the toolbar separator item.  var templateNode = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                              "toolbarseparator");  templateNode.id = "separator";  wrapPaletteItem(templateNode, currentRow, null);  // Add the toolbar spring item.  templateNode = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                              "toolbarspring");  templateNode.id = "spring";  templateNode.flex = 1;  wrapPaletteItem(templateNode, currentRow, null);  // Add the toolbar spacer item.  templateNode = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                              "toolbarspacer");  templateNode.id = "spacer";  templateNode.flex = 1;  wrapPaletteItem(templateNode, currentRow, null);  var rowSlot = 3;  var currentItems = getCurrentItemIds();  templateNode = gToolbox.palette.firstChild;  while (templateNode) {    // Check if the item is already in a toolbar before adding it to the palette.    if (!(templateNode.id in currentItems)) {      var paletteItem = templateNode.cloneNode(true);      if (rowSlot == kRowMax) {        // Append the old row.        paletteBox.appendChild(currentRow);        // Make a new row.        currentRow = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                              "hbox");        currentRow.setAttribute("class", "paletteRow");        rowSlot = 0;      }      ++rowSlot;      wrapPaletteItem(paletteItem, currentRow, null);    }        templateNode = templateNode.nextSibling;  }  if (currentRow) {     fillRowWithFlex(currentRow);    paletteBox.appendChild(currentRow);  }}/** * Creates a new palette item for a cloned template node and * adds it to the last slot in the palette. */function appendPaletteItem(aItem){  var paletteBox = document.getElementById("palette-box");  var lastRow = paletteBox.lastChild;  var lastSpacer = lastRow.lastChild;     if (lastSpacer.localName != "spacer") {    // The current row is full, so we have to create a new row.    lastRow = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                        "hbox");    lastRow.setAttribute("class", "paletteRow");    paletteBox.appendChild(lastRow);        wrapPaletteItem(aItem, lastRow, null);    fillRowWithFlex(lastRow);  } else {    // Decrement the flex of the last spacer or remove it entirely.    var flex = lastSpacer.getAttribute("flex");    if (flex == 1) {      lastRow.removeChild(lastSpacer);      lastSpacer = null;    } else      lastSpacer.setAttribute("flex", --flex);    // Insert the wrapper where the last spacer was.    wrapPaletteItem(aItem, lastRow, lastSpacer);  }}function fillRowWithFlex(aRow){  var remainingFlex = kRowMax - aRow.childNodes.length;  if (remainingFlex > 0) {    var spacer = document.createElementNS("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul",                                          "spacer");    spacer.setAttribute("flex", remainingFlex);    aRow.appendChild(spacer);  }}/** * Makes sure that an item that has been cloned from a template * is stripped of all properties that may adversely affect it's * appearance in the palette. */function cleanUpItemForPalette(aItem, aWrapper)

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?