📄 dommenu.js
字号:
/** $Id: domMenu.js,v 1.1 2006/12/26 08:24:23 linhdh Exp $ */// {{{ license/* * Copyright 2002-2005 Dan Allen, Mojavelinux.com (dan.allen@mojavelinux.com) * * Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */// }}}// {{{ intro/** * Title: DOM Menu Library * Version: 0.3.7 * * Summary: * A widget library for creating dynamic "popout" menus on webpages. The menu can * either be horizontal or vertical, and can open in either direction. It has * both edge detection and obstruction detection (for browsers that cannot * hide select boxes or flash animations). The styles for the menu items are * controlled entirely through CSS. The menus are created and destroyed using * the DOM. Menu configuration is done using a custom Hash() class. * * Dependency: domLib.js version 0.72 * * Maintainer: Dan Allen <dan@mojavelinux.com> * Contributors: * Jason Rust <jrust@rustyparts.com> * * License: Apache 2.0 * However, if you use this library, you earn the position of official bug * reporter :) Please post questions or problem reports to the newsgroup: * * http://groups.google.com/group/dom-menu * * If you are doing this for commercial work, perhaps you could send me a few * Starbucks Coffee gift dollars or PayPal bucks to encourage future * developement (NOT REQUIRED). E-mail me for my snail mail address. * * Homepage: http://www.mojavelinux.com/projects/dommenu/ * * Freshmeat Project: http://freshmeat.net/projects/dommenu/?topic_id=92 * * Updated: $Date: 2006/12/26 08:24:23 $ * * Supported Browsers: * Mozilla (Gecko), IE 5.0+, IE on Mac, Safari, Konqueror, Opera 7+ * * If there is a non-negative click open delay, then any uri of the element will be ignored * * The alternate contents for a hover element are treated by creating to <span> wrapper elements * and then alternating the display of them. This avoids the need for innerHTML, which can * do nasty things to the browsers. If <span> turns out to be a bad choice for tags, then a * non-HTML element can be used instead. * * Dev Notes: * - added cellSpacing = 0 for domLib_isMacIE (two places) * - seems that Safari and Firefox share an offset problem of menu under parent (pmp example) * - must use createTextNode() to add the "\n" that is required for Mac to * render the appendChild element (two places); this might be the solution for * the sub menus as well * - Safari seems to have a problem with offsetTop if a descendent of body has a margin; solution * is to use padding on the body */// }}}// {{{ settings (editable)var domMenu_data = new Hash();var domMenu_settings = new Hash();domMenu_settings.set('global', new Hash( 'menuBarClass', 'domMenu_menuBar', 'menuElementClass', 'domMenu_menuElement', 'menuElementHoverClass', 'domMenu_menuElementHover', 'menuElementActiveClass', 'domMenu_menuElementHover', 'subMenuBarClass', 'domMenu_subMenuBar', 'subMenuElementClass', 'domMenu_subMenuElement', 'subMenuElementHoverClass', 'domMenu_subMenuElementHover', 'subMenuElementActiveClass', 'domMenu_subMenuElementHover', 'subMenuElementHeadingClass', 'domMenu_subMenuElementHeading', 'subMenuTargetFrame', false, 'targetDocumentXOrigin', 0, 'targetDocumentYOrigin', 0, 'menuBarWidth', '100%', 'subMenuMinWidth', 'inherit', 'distributeSpace', true, 'axis', 'horizontal', 'verticalExpand', 'south', 'horizontalExpand', 'east', 'expandMenuArrowUrl', 'arrow.gif', 'subMenuWidthCorrection', 0, 'verticalSubMenuOffsetY', 0, 'verticalSubMenuOffsetX', 0, 'horizontalSubMenuOffsetX', 0, 'horizontalSubMenuOffsetY', 0, 'screenPadding', 0, 'openMouseoverMenuDelay', 300, 'openMousedownMenuDelay', -1, 'closeMouseoutMenuDelay', 800, 'closeClickMenuDelay', -1, 'openMouseoverSubMenuDelay', 300, 'openClickSubMenuDelay', -1, 'closeMouseoutSubMenuDelay', 300, 'closeClickSubMenuDelay', -1, 'baseZIndex', 100, 'baseUri', ''));// }}}// {{{ globals (DO NOT EDIT)/** * The data for the menu is stored here, loaded from an external file * @hash domMenu_data */var domMenu_data;var domMenu_selectElements;var domMenu_scrollbarWidth = 14;var domMenu_eventTo = domLib_isIE ? 'toElement' : 'relatedTarget';var domMenu_eventFrom = domLib_isIE ? 'fromElement' : 'relatedTarget';var domMenu_activeElement = new Hash();/** * Array of hashes listing the timouts currently running for opening/closing menus * @array domMenu_timeouts */var domMenu_timeouts = [];domMenu_timeouts['open'] = new Hash();domMenu_timeouts['close'] = new Hash();/** * Style to use for a link pointer, which is different between Gecko and IE * @var domMenu_pointerStyle */var domMenu_pointerStyle = domLib_isIE ? 'hand' : 'pointer';// }}}// {{{ domMenu_activate()function domMenu_activate(in_containerId, in_disableWarning){ var container; var data; // make sure we can use the menu system if (!domLib_useLibrary) { if (!in_disableWarning) { alert('domMenu: Browser not supported. Menu will be disabled.'); } return; } // make sure that this is a valid menu, // and that the menu actually has data if (!(container = document.getElementById(in_containerId)) || !(data = domMenu_data.get(in_containerId)) || data.numericLength == 0) { if (!in_disableWarning) { alert('domMenu: Menu failed to load.'); } return; } if (domLib_isIE && window.attachEvent) { window.attachEvent('onunload', domMenu_unloadEventCache); } // start with the global settings and merge in the local changes if (!domMenu_settings.has(in_containerId)) { domMenu_settings.set(in_containerId, new Hash()); } var settings = domMenu_settings.get(in_containerId); for (var i in domMenu_settings.get('global').elementData) { if (!settings.has(i)) { settings.set(i, domMenu_settings.get('global').get(i)); } } // populate the zero level element container.data = new Hash( 'parentElement', false, 'numChildren', data.numericLength, 'childElements', new Hash(), 'level', 0, 'index', 1 ); // if we choose to distribute either height or width, determine ratio of each cell var distributeRatio = Math.round(100/container.data.get('numChildren')) + '%'; // the first menu is the rootMenu, which is a child of the zero level element var rootMenu = document.createElement('div'); rootMenu.id = in_containerId + '-0'; rootMenu.className = settings.get('menuBarClass'); container.data.set('subMenu', rootMenu); var rootMenuTable = rootMenu.appendChild(document.createElement('table')); if (domLib_isKonq || domLib_isMacIE) { rootMenuTable.cellSpacing = 0; } rootMenuTable.style.border = 0; rootMenuTable.style.borderCollapse = 'collapse'; rootMenuTable.style.width = settings.get('menuBarWidth'); var rootMenuTableBody = rootMenuTable.appendChild(document.createElement('tbody')); var numSiblings = container.data.get('numChildren'); for (var index = 1; index <= numSiblings; index++) { // create a row the first time if horizontal or each time if vertical if (index == 1 || settings.get('axis') == 'vertical') { var rootMenuTableRow = rootMenuTableBody.appendChild(document.createElement('tr')); } // create an instance of the root level menu element var rootMenuTableCell = rootMenuTableRow.appendChild(document.createElement('td')); rootMenuTableCell.style.padding = 0; rootMenuTableCell.id = in_containerId + '-' + index; // add element to list of parent children container.data.get('childElements').set(rootMenuTableCell.id, rootMenuTableCell); // assign the settings to the root level element // NOTE: this is a problem if two menus are using the same data rootMenuTableCell.data = data.get(index); rootMenuTableCell.data.merge(new Hash( 'basename', in_containerId, 'parentElement', container, 'numChildren', rootMenuTableCell.data.numericLength, 'childElements', new Hash(), 'offsets', new Hash(), 'level', container.data.get('level') + 1, 'index', index )); // assign the styles rootMenuTableCell.style.cursor = 'default'; if (settings.get('axis') == 'horizontal') { if (settings.get('distributeSpace')) { rootMenuTableCell.style.width = distributeRatio; } } // Needed for when the text wraps rootMenuTableCell.style.verticalAlign = 'top'; var rootElement = rootMenuTableCell.appendChild(document.createElement('div')); rootElement.className = settings.get('menuElementClass'); // fill in the menu element contents var spanElement = rootElement.appendChild(document.createElement('span')); // can't use createTextNode() because there might be img tags in the contents spanElement.innerHTML = rootMenuTableCell.data.get('contents').replace(/\/\/\//, settings.get('baseUri')); // add hover contents if needed if (rootMenuTableCell.data.has('contentsHover')) { spanElement = rootElement.appendChild(document.createElement('span')); spanElement.style.display = 'none'; spanElement.innerHTML = rootMenuTableCell.data.get('contentsHover').replace(/\/\/\//, settings.get('baseUri')); } // MacIE has to have a newline at the end or else it barfs // additionally, it MUST be added using createTextNode() or IE will crash! if (domLib_isMacIE) { rootMenuTableCell.appendChild(document.createTextNode("\n")); } // attach the events rootMenuTableCell.onmouseover = domMenu_openMenuOnmouseoverHandler; rootMenuTableCell.onmouseout = domMenu_closeMenuHandler; if (settings.get('openMousedownMenuDelay') >= 0 && rootMenuTableCell.data.get('numChildren')) { rootMenuTableCell.onmousedown = domMenu_openMenuOnmousedownHandler; // cancel mouseup so that it doesn't propogate to global mouseup event rootMenuTableCell.onmouseup = domLib_cancelBubble; if (domLib_isIE) { rootMenuTableCell.ondblclick = domMenu_openMenuOnmousedownHandler; } } else if (rootMenuTableCell.data.get('uri')) { rootMenuTableCell.style.cursor = domMenu_pointerStyle; rootMenuTableCell.onclick = domMenu_resolveLinkHandler; } // prevent highlighting of text if (domLib_isIE) { rootMenuTableCell.onselectstart = makeFalse; } rootMenuTableCell.oncontextmenu = makeFalse; } // add the menu rootMenu to the zero level element rootMenu = container.appendChild(rootMenu); if (domLib_detectObstructionsEnabled) { // even though most cases the top level menu does not go away, it could // if this menu system is used by another process domLib_detectObstructions(rootMenu, false, false); }}// }}}// {{{ domMenu_activateSubMenu()function domMenu_activateSubMenu(in_parentElement){ // NOTE: submenus not supported in MacIE because of problems using // appendChild on document.body if (domLib_isMacIE) { return; } // see if submenu already exists if (in_parentElement.data.has('subMenu')) { domMenu_toggleSubMenu(in_parentElement, 'visible'); return; } var settings = domMenu_settings.get(in_parentElement.data.get('basename')); var targetDoc = document; var targetFrame = settings.get('subMenuTargetFrame'); if (targetFrame) { targetDoc = targetFrame.document; } // build the submenu var menu = targetDoc.createElement('div'); menu.id = in_parentElement.id + '-0'; menu.className = settings.get('subMenuBarClass'); menu.style.zIndex = settings.get('baseZIndex'); menu.style.position = 'absolute'; // position the menu in the upper left corner hidden so that we can work on it menu.style.visibility = 'hidden'; menu.style.top = 0; menu.style.left = 0; in_parentElement.data.set('subMenu', menu); var menuTable = menu.appendChild(targetDoc.createElement('table')); // ** opera wants to make absolute tables width 100% ** if (domLib_isOpera) { menuTable.style.width = '1px'; menuTable.style.whiteSpace = 'nowrap'; } if (domLib_isKonq || domLib_isMacIE) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -