[vhffs-dev] [1402] New design for home page, subscribe and lost password. |
[ Thread Index | Date Index | More vhffs.org/vhffs-dev Archives ]
Revision: 1402 Author: beuss Date: 2009-05-23 15:44:53 +0200 (Sat, 23 May 2009) Log Message: ----------- New design for home page, subscribe and lost password. Still strange JS issues on subscribe, will be fixed soon Modified Paths: -------------- branches/vhffs-design/vhffs-api/src/Vhffs/User.pm branches/vhffs-design/vhffs-panel/Makefile.am branches/vhffs-design/vhffs-panel/auth.pl branches/vhffs-design/vhffs-panel/favicon.ico branches/vhffs-design/vhffs-panel/js/dojo/back.js branches/vhffs-design/vhffs-panel/lost.pl branches/vhffs-design/vhffs-panel/subscribe.pl branches/vhffs-design/vhffs-panel/templates/Makefile.am branches/vhffs-design/vhffs-themes/Makefile.am branches/vhffs-design/vhffs-themes/light-grey/main.css Added Paths: ----------- branches/vhffs-design/vhffs-api/src/Vhffs/Panel/Anonymous.pm branches/vhffs-design/vhffs-panel/js/anonymous.js branches/vhffs-design/vhffs-panel/js/dijit/Tooltip.js branches/vhffs-design/vhffs-panel/js/dijit/dijit.js branches/vhffs-design/vhffs-panel/js/dijit/form/ branches/vhffs-design/vhffs-panel/js/dijit/form/TextBox.js branches/vhffs-design/vhffs-panel/js/dijit/form/ValidationTextBox.js branches/vhffs-design/vhffs-panel/js/dijit/form/nls/ branches/vhffs-design/vhffs-panel/js/dijit/form/nls/validate.js branches/vhffs-design/vhffs-panel/js/dojo/dojo.js branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js branches/vhffs-design/vhffs-panel/js/dojo/i18n.js branches/vhffs-design/vhffs-panel/templates/content/ branches/vhffs-design/vhffs-panel/templates/content/anonymous/ branches/vhffs-design/vhffs-panel/templates/content/anonymous/login.tt branches/vhffs-design/vhffs-panel/templates/content/anonymous/lost-password.tt branches/vhffs-design/vhffs-panel/templates/content/anonymous/subscribe.tt branches/vhffs-design/vhffs-panel/templates/layouts/ branches/vhffs-design/vhffs-panel/templates/layouts/anonymous.tt branches/vhffs-design/vhffs-themes/light-grey/img/popupMenuBg.gif branches/vhffs-design/vhffs-themes/light-grey/img/tooltipConnectorLeft.png branches/vhffs-design/vhffs-themes/light-grey/img/warning.png Removed Paths: ------------- branches/vhffs-design/vhffs-panel/js/dijit/dijit.js branches/vhffs-design/vhffs-panel/js/dojo/dojo.js branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js branches/vhffs-design/vhffs-panel/lost_ack.pl branches/vhffs-design/vhffs-panel/templates/main/lost.tmpl branches/vhffs-design/vhffs-panel/templates/main/lost_failed.tmpl branches/vhffs-design/vhffs-panel/templates/main/lost_ok.tmpl branches/vhffs-design/vhffs-panel/templates/user/create.tmpl branches/vhffs-design/vhffs-panel/templates/user/create_complete.tmpl
Added: branches/vhffs-design/vhffs-api/src/Vhffs/Panel/Anonymous.pm =================================================================== --- branches/vhffs-design/vhffs-api/src/Vhffs/Panel/Anonymous.pm (rev 0) +++ branches/vhffs-design/vhffs-api/src/Vhffs/Panel/Anonymous.pm 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,86 @@ +#!%PERL% +# Copyright (c) vhffs project and its contributors +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +#2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in +# the documentation and/or other materials provided with the +# distribution. +#3. Neither the name of vhffs nor the names of its contributors +# may be used to endorse or promote products derived from this +# software without specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +#"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +#LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +#FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +#COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +#INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +#BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +#CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN +# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +# POSSIBILITY OF SUCH DAMAGE. + +use strict; +use utf8; + +# Panel class for displaying pages for anonymous +# users + +package Vhffs::Panel::Anonymous; + +use base qw(Vhffs::Panel); + +use locale; +use Locale::gettext; +use POSIX qw(locale_h); + +use Template; + +use lib '%VHFFS_LIB_DIR%'; +use Vhffs::Tag; +use Vhffs::Functions; + +# Trying to have a singleton to allow +# require to keep infos/errors +my $panel; + +sub new { + my $class = shift; + $panel = $class->SUPER::new(@_) unless($panel); + $panel->check_public(); + return $panel; +} + +sub render { + my ($self, $file, $vars) = @_; + my $vhffs = $self->{vhffs}; + my $conf = $vhffs->get_config; + + $vars = {} unless(defined $vars); + + my $default_vars = { + subscribe => Vhffs::Functions::strtobool($vhffs->get_config->get_allow_subscribe), + public => $self->is_public, + publicurl => $vhffs->get_config->get_panel->{'url_public'}, + theme => $conf->get_panel->{default_theme} + }; + + $vars = {%$default_vars, %$vars}; + + # Handling ajax stuff + unless($self->{is_ajax_request}) { + } + + $self->SUPER::render($file, $vars, $self->{templatedir}.'/panel/', 'layouts/anonymous.tt'); +} + +1; Modified: branches/vhffs-design/vhffs-api/src/Vhffs/User.pm =================================================================== --- branches/vhffs-design/vhffs-api/src/Vhffs/User.pm 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-api/src/Vhffs/User.pm 2009-05-23 13:44:53 UTC (rev 1402) @@ -87,6 +87,7 @@ =cut +our $username_regex = '^[a-z0-9]{3,12}$'; sub _new { my ($class, $main, $uid, $gid, $oid, $username, $passwd, $homedir, $shell, $admin, $firstname, $lastname, $address, $zipcode, $city, $country, $mail, $gpg_key, $note, $language, $theme, $lastloginpanel, $date_creation, $description, $state) = @_; @@ -144,7 +145,7 @@ sub check_username($) { my $username = shift; - return ( defined($username) && ($username =~ /^[a-z0-9]{3,12}$/) ); + return ( defined($username) && ($username =~ /$username_regex/) ); } =pod @@ -179,6 +180,8 @@ local $dbh->{RaiseError} = 1; $dbh->begin_work; eval { + use Vhffs::Acl; + # object(owner_uid) references user(uid) and user(object_id) object(object_id) # so we have to tell pg that constraints shouldn't be checked before the end # of transaction @@ -203,9 +206,13 @@ my $group = Vhffs::Group::create($main, $username, undef, $uid, $gid); die('Error creating group') unless (defined $group); $group->set_status(Vhffs::Constants::ACTIVATED); - $group->set_quota( $userconf->{'default_quota'} || 1 ); + + $group->set_quota( $userconf->{'default_quota'} || 1 ); $group->commit; + Vhffs::Acl::add_acl( $user , $user , Vhffs::Constants::ACL_DELETE , $main ); + Vhffs::Acl::add_acl( $group , $user , Vhffs::Constants::ACL_DENIED , $main ); + $dbh->commit; $user = get_by_uid($main, $uid); }; Modified: branches/vhffs-design/vhffs-panel/Makefile.am =================================================================== --- branches/vhffs-design/vhffs-panel/Makefile.am 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/Makefile.am 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,10 +1,16 @@ javascripts = js/prototype.js \ js/commons.js \ js/dijit/dijit.js \ + js/dijit/Tooltip.js \ + js/dijit/form/TextBox.js \ + js/dijit/form/ValidationTextBox.js \ + js/dijit/form/nls/validate.js \ js/dojo/back.js \ js/dojo/dojo.js \ + js/dojo/i18n.js \ js/dojo/resources/blank.gif \ js/dojo/resources/iframe_history.html \ + js/anonymous.js \ js/public.js \ js/tooltip.js \ js/vhffs/Common.js \ @@ -25,7 +31,6 @@ getavatar.pl \ history.pl \ lost.pl \ - lost_ack.pl \ panel.pl \ show_code.pl \ play_code.pl \ Modified: branches/vhffs-design/vhffs-panel/auth.pl =================================================================== --- branches/vhffs-design/vhffs-panel/auth.pl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/auth.pl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,4 +1,4 @@ -#!%PERL% -w +#!/usr/bin/perl -w # Copyright (c) vhffs project and its contributors # All rights reserved. # @@ -29,30 +29,27 @@ # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE # POSSIBILITY OF SUCH DAMAGE. +use strict; +use utf8; -require 5.004; -use utf8; -use POSIX; -use strict; +use POSIX qw(locale_h); use locale; use Locale::gettext; -use HTML::Template; -use CGI; -use lib '%VHFFS_LIB_DIR%'; -use Vhffs::Main; -use Vhffs::Panel::Main; -use Vhffs::Panel::Commons; + +use lib '/usr/share/vhffs/api'; use Vhffs::Constants; +use Vhffs::Panel::Anonymous; +use Vhffs::User; -my $panel = new Vhffs::Panel::Main(); +my $panel = new Vhffs::Panel::Anonymous(); exit 0 unless $panel; -my $vhffs = $panel->{'vhffs'}; -my $templatedir = $panel->{'templatedir'}; +my $vhffs = $panel->{vhffs}; my $cgi = $panel->{cgi}; -my $loginsubmitted = defined( $cgi->param('login_submit') ); +my $loginsubmitted = defined( $cgi->param('username') ); my $logoutsubmitted = defined( $cgi->param('logout') ); + if( $loginsubmitted ) { # User tried to log in # we try to clean the previous session @@ -86,14 +83,45 @@ my $themecookie = new CGI::Cookie( -name=> 'theme', -value=>$user->get_theme, -expires=>'+10y' ); my $langcookie = new CGI::Cookie( -name=>'language', -value=>$user->get_lang, -expires=>'+10y' ); - # Set last login panel to current time - $user->update_lastloginpanel; - $user->commit; + # Set last login panel to current time + $user->update_lastloginpanel; + $user->commit; $panel->redirect('/panel.pl', [$sessioncookie, $themecookie, $langcookie]); } +} elsif( $logoutsubmitted ) { + # Delete existing session + my $oldsid = CGI->cookie( CGI::Session::name() ); + if( defined $oldsid ) { + my $oldsession = new CGI::Session(undef, $oldsid, {Directory=>'/tmp'}); + $oldsession->delete(); + } + + $panel->add_info( gettext('You left your VHFFS session!') ); } +my $showstats = Vhffs::Functions::strtobool($vhffs->get_config->get_panel->{stats_on_home}); + + +my $vars = { + hostername => $vhffs->get_config->get_host_name, + hostersite => $vhffs->get_config->get_host_website, + showstats => $showstats +}; + +if($showstats) { + my $stats = new Vhffs::Stats( $vhffs ); + $vars->{users_count} = $stats->get_user_total; + $vars->{groups_count} = $stats->get_groups_activated; +} + +$panel->render('content/anonymous/login.tt', $vars); + +__END__ + +my $templatedir = $panel->{'templatedir'}; + + if( $logoutsubmitted ) { #clean session my $oldsid = CGI->cookie( CGI::Session::name() ); Modified: branches/vhffs-design/vhffs-panel/favicon.ico =================================================================== (Binary files differ) Added: branches/vhffs-design/vhffs-panel/js/anonymous.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/anonymous.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/anonymous.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,44 @@ +/* + * Copyright (c) vhffs project and its contributors + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name of vhffs nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER + * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + + /* + * JavaScript function used on the anonymous + * panel pages (login, subscribe, etc.) + */ + + dojo.require('vhffs.Common'); + + + dojo.addOnLoad(function() { + vhffs.Common.ajaxizeLinks(dojo.byId('content-panel-anonymous')); +}); + Added: branches/vhffs-design/vhffs-panel/js/dijit/Tooltip.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/Tooltip.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dijit/Tooltip.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,160 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + + +if(!dojo._hasResource["dijit.Tooltip"]){ +dojo._hasResource["dijit.Tooltip"]=true; +dojo.provide("dijit.Tooltip"); +dojo.require("dijit._Widget"); +dojo.require("dijit._Templated"); +dojo.declare("dijit._MasterTooltip",[dijit._Widget,dijit._Templated],{duration:dijit.defaultDuration,templateString:"<div class=\"dijitTooltip dijitTooltipLeft\" id=\"dojoTooltip\">\n\t<div class=\"dijitTooltipContainer dijitTooltipContents\" dojoAttachPoint=\"containerNode\" waiRole='alert'></div>\n\t<div class=\"dijitTooltipConnector\"></div>\n</div>\n",postCreate:function(){ +dojo.body().appendChild(this.domNode); +this.bgIframe=new dijit.BackgroundIframe(this.domNode); +this.fadeIn=dojo.fadeIn({node:this.domNode,duration:this.duration,onEnd:dojo.hitch(this,"_onShow")}); +this.fadeOut=dojo.fadeOut({node:this.domNode,duration:this.duration,onEnd:dojo.hitch(this,"_onHide")}); +},show:function(_1,_2,_3){ +if(this.aroundNode&&this.aroundNode===_2){ +return; +} +if(this.fadeOut.status()=="playing"){ +this._onDeck=arguments; +return; +} +this.containerNode.innerHTML=_1; +this.domNode.style.top=(this.domNode.offsetTop+1)+"px"; +var _4={}; +var _5=this.isLeftToRight(); +dojo.forEach((_3&&_3.length)?_3:dijit.Tooltip.defaultPosition,function(_6){ +switch(_6){ +case "after": +_4[_5?"BR":"BL"]=_5?"BL":"BR"; +break; +case "before": +_4[_5?"BL":"BR"]=_5?"BR":"BL"; +break; +case "below": +_4[_5?"BL":"BR"]=_5?"TL":"TR"; +_4[_5?"BR":"BL"]=_5?"TR":"TL"; +break; +case "above": +default: +_4[_5?"TL":"TR"]=_5?"BL":"BR"; +_4[_5?"TR":"TL"]=_5?"BR":"BL"; +break; +} +}); +var _7=dijit.placeOnScreenAroundElement(this.domNode,_2,_4,dojo.hitch(this,"orient")); +dojo.style(this.domNode,"opacity",0); +this.fadeIn.play(); +this.isShowingNow=true; +this.aroundNode=_2; +},orient:function(_8,_9,_a){ +_8.className="dijitTooltip "+{"BL-TL":"dijitTooltipBelow dijitTooltipABLeft","TL-BL":"dijitTooltipAbove dijitTooltipABLeft","BR-TR":"dijitTooltipBelow dijitTooltipABRight","TR-BR":"dijitTooltipAbove dijitTooltipABRight","BR-BL":"dijitTooltipRight","BL-BR":"dijitTooltipLeft"}[_9+"-"+_a]; +},_onShow:function(){ +if(dojo.isIE){ +this.domNode.style.filter=""; +} +},hide:function(_b){ +if(this._onDeck&&this._onDeck[1]==_b){ +this._onDeck=null; +}else{ +if(this.aroundNode===_b){ +this.fadeIn.stop(); +this.isShowingNow=false; +this.aroundNode=null; +this.fadeOut.play(); +}else{ +} +} +},_onHide:function(){ +this.domNode.style.cssText=""; +if(this._onDeck){ +this.show.apply(this,this._onDeck); +this._onDeck=null; +} +}}); +dijit.showTooltip=function(_c,_d,_e){ +if(!dijit._masterTT){ +dijit._masterTT=new dijit._MasterTooltip(); +} +return dijit._masterTT.show(_c,_d,_e); +}; +dijit.hideTooltip=function(_f){ +if(!dijit._masterTT){ +dijit._masterTT=new dijit._MasterTooltip(); +} +return dijit._masterTT.hide(_f); +}; +dojo.declare("dijit.Tooltip",dijit._Widget,{label:"",showDelay:400,connectId:[],position:[],_setConnectIdAttr:function(ids){ +this._connectNodes=[]; +this.connectId=dojo.isArrayLike(ids)?ids:[ids]; +dojo.forEach(this.connectId,function(id){ +var _12=dojo.byId(id); +if(_12){ +this._connectNodes.push(_12); +dojo.forEach(["onMouseEnter","onMouseLeave","onFocus","onBlur"],function(_13){ +this.connect(_12,_13.toLowerCase(),"_"+_13); +},this); +if(dojo.isIE){ +_12.style.zoom=1; +} +} +},this); +},postCreate:function(){ +dojo.addClass(this.domNode,"dijitTooltipData"); +},_onMouseEnter:function(e){ +this._onHover(e); +},_onMouseLeave:function(e){ +this._onUnHover(e); +},_onFocus:function(e){ +this._focus=true; +this._onHover(e); +this.inherited(arguments); +},_onBlur:function(e){ +this._focus=false; +this._onUnHover(e); +this.inherited(arguments); +},_onHover:function(e){ +if(!this._showTimer){ +var _19=e.target; +this._showTimer=setTimeout(dojo.hitch(this,function(){ +this.open(_19); +}),this.showDelay); +} +},_onUnHover:function(e){ +if(this._focus){ +return; +} +if(this._showTimer){ +clearTimeout(this._showTimer); +delete this._showTimer; +} +this.close(); +},open:function(_1b){ +_1b=_1b||this._connectNodes[0]; +if(!_1b){ +return; +} +if(this._showTimer){ +clearTimeout(this._showTimer); +delete this._showTimer; +} +dijit.showTooltip(this.label||this.domNode.innerHTML,_1b,this.position); +this._connectNode=_1b; +},close:function(){ +if(this._connectNode){ +dijit.hideTooltip(this._connectNode); +delete this._connectNode; +} +if(this._showTimer){ +clearTimeout(this._showTimer); +delete this._showTimer; +} +},uninitialize:function(){ +this.close(); +}}); +dijit.Tooltip.defaultPosition=["after","before"]; +} Deleted: branches/vhffs-design/vhffs-panel/js/dijit/dijit.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/dijit.js 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/js/dijit/dijit.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,20 +0,0 @@ -/* - Copyright (c) 2004-2008, The Dojo Foundation - All Rights Reserved. - - Licensed under the Academic Free License version 2.1 or above OR the - modified BSD license. For more information on Dojo licensing, see: - - http://dojotoolkit.org/book/dojo-book-0-9/introduction/licensing -*/ - -/* - This is a compiled version of Dojo, built for deployment and not for - development. To get an editable version, please visit: - - http://dojotoolkit.org - - for documentation and information on getting the source. -*/ - -if(!dojo._hasResource["dijit._base.focus"]){dojo._hasResource["dijit._base.focus"]=true;dojo.provide("dijit._base.focus");dojo.mixin(dijit,{_curFocus:null,_prevFocus:null,isCollapsed:function(){var _1=dojo.global;var _2=dojo.doc;if(_2.selection){return !_2.selection.createRange().text;}else{var _3=_1.getSelection();if(dojo.isString(_3)){return !_3;}else{return _3.isCollapsed||!_3.toString();}}},getBookmark:function(){var _4,_5=dojo.doc.selection;if(_5){var _6=_5.createRange();if(_5.type.toUpperCase()=="CONTROL"){if(_6.length){_4=[];var i=0,_8=_6.length;while(i<_8){_4.push(_6.item(i++));}}else{_4=null;}}else{_4=_6.getBookmark();}}else{if(window.getSelection){_5=dojo.global.getSelection();if(_5){_6=_5.getRangeAt(0);_4=_6.cloneRange();}}else{console.warn("No idea how to store the current selection for this browser!");}}return _4;},moveToBookmark:function(_9){var _a=dojo.doc;if(_a.selection){var _b;if(dojo.isArray(_9)){_b=_a.body.createControlRange();dojo.forEach(_9,"range.addElement(item)");}else{_b=_a.selection.createRange();_b.moveToBookmark(_9);}_b.select();}else{var _c=dojo.global.getSelection&&dojo.global.getSelection();if(_c&&_c.removeAllRanges){_c.removeAllRanges();_c.addRange(_9);}else{console.warn("No idea how to restore selection for this browser!");}}},getFocus:function(_d,_e){return {node:_d&&dojo.isDescendant(dijit._curFocus,_d.domNode)?dijit._prevFocus:dijit._curFocus,bookmark:!dojo.withGlobal(_e||dojo.global,dijit.isCollapsed)?dojo.withGlobal(_e||dojo.global,dijit.getBookmark):null,openedForWindow:_e};},focus:function(_f){if(!_f){return;}var _10="node" in _f?_f.node:_f,_11=_f.bookmark,_12=_f.openedForWindow;if(_10){var _13=(_10.tagName.toLowerCase()=="iframe")?_10.contentWindow:_10;if(_13&&_13.focus){try{_13.focus();}catch(e){}}dijit._onFocusNode(_10);}if(_11&&dojo.withGlobal(_12||dojo.global,dijit.isCollapsed)){if(_12){_12.focus();}try{dojo.withGlobal(_12||dojo.global,dijit.moveToBookmark,null,[_11]);}catch(e){}}},_activeStack:[],registerWin:function(_14){if(!_14){_14=window;}dojo.connect(_14.document,"onmousedown",function(evt){dijit._justMouseDowned=true;setTimeout(function(){dijit._justMouseDowned=false;},0);dijit._onTouchNode(evt.target||evt.srcElement);});var _16=_14.document.body||_14.document.getElementsByTagName("body")[0];if(_16){if(dojo.isIE){_16.attachEvent("onactivate",function(evt){if(evt.srcElement.tagName.toLowerCase()!="body"){dijit._onFocusNode(evt.srcElement);}});_16.attachEvent("ondeactivate",function(evt){dijit._onBlurNode(evt.srcElement);});}else{_16.addEventListener("focus",function(evt){dijit._onFocusNode(evt.target);},true);_16.addEventListener("blur",function(evt){dijit._onBlurNode(evt.target);},true);}}_16=null;},_onBlurNode:function(_1b){dijit._prevFocus=dijit._curFocus;dijit._curFocus=null;if(dijit._justMouseDowned){return;}if(dijit._clearActiveWidgetsTimer){clearTimeout(dijit._clearActiveWidgetsTimer);}dijit._clearActiveWidgetsTimer=setTimeout(function(){delete dijit._clearActiveWidgetsTimer;dijit._setStack([]);dijit._prevFocus=null;},100);},_onTouchNode:function(_1c){if(dijit._clearActiveWidgetsTimer){clearTimeout(dijit._clearActiveWidgetsTimer);delete dijit._clearActiveWidgetsTimer;}var _1d=[];try{while(_1c){if(_1c.dijitPopupParent){_1c=dijit.byId(_1c.dijitPopupParent).domNode;}else{if(_1c.tagName&&_1c.tagName.toLowerCase()=="body"){if(_1c===dojo.body()){break;}_1c=dijit.getDocumentWindow(_1c.ownerDocument).frameElement;}else{var id=_1c.getAttribute&&_1c.getAttribute("widgetId");if(id){_1d.unshift(id);}_1c=_1c.parentNode;}}}}catch(e){}dijit._setStack(_1d);},_onFocusNode:function(_1f){if(_1f&&_1f.tagName&&_1f.tagName.toLowerCase()=="body"){return;}dijit._onTouchNode(_1f);if(_1f==dijit._curFocus){return;}if(dijit._curFocus){dijit._prevFocus=dijit._curFocus;}dijit._curFocus=_1f;dojo.publish("focusNode",[_1f]);},_setStack:function(_20){var _21=dijit._activeStack;dijit._activeStack=_20;for(var _22=0;_22<Math.min(_21.length,_20.length);_22++){if(_21[_22]!=_20[_22]){break;}}for(var i=_21.length-1;i>=_22;i--){var _24=dijit.byId(_21[i]);if(_24){_24._focused=false;_24._hasBeenBlurred=true;if(_24._onBlur){_24._onBlur();}if(_24._setStateClass){_24._setStateClass();}dojo.publish("widgetBlur",[_24]);}}for(i=_22;i<_20.length;i++){_24=dijit.byId(_20[i]);if(_24){_24._focused=true;if(_24._onFocus){_24._onFocus();}if(_24._setStateClass){_24._setStateClass();}dojo.publish("widgetFocus",[_24]);}}}});dojo.addOnLoad(dijit.registerWin);}if(!dojo._hasResource["dijit._base.manager"]){dojo._hasResource["dijit._base.manager"]=true;dojo.provide("dijit._base.manager");dojo.declare("dijit.WidgetSet",null,{constructor:function(){this._hash={};},add:function(_25){if(this._hash[_25.id]){throw new Error("Tried to register widget with id=="+_25.id+" but that id is already registered");}this._hash[_25.id]=_25;},remove:function(id){delete this._hash[id];},forEach:function(_27){for(var id in this._hash){_27(this._hash[id]);}},filter:function(_29){var res=new dijit.WidgetSet();this.forEach(function(_2b){if(_29(_2b)){res.add(_2b);}});return res;},byId:function(id){return this._hash[id];},byClass:function(cls){return this.filter(function(_2e){return _2e.declaredClass==cls;});}});dijit.registry=new dijit.WidgetSet();dijit._widgetTypeCtr={};dijit.getUniqueId=function(_2f){var id;do{id=_2f+"_"+(_2f in dijit._widgetTypeCtr?++dijit._widgetTypeCtr[_2f]:dijit._widgetTypeCtr[_2f]=0);}while(dijit.byId(id));return id;};if(dojo.isIE){dojo.addOnUnload(function(){dijit.registry.forEach(function(_31){_31.destroy();});});}dijit.byId=function(id){return (dojo.isString(id))?dijit.registry.byId(id):id;};dijit.byNode=function(_33){return dijit.registry.byId(_33.getAttribute("widgetId"));};dijit.getEnclosingWidget=function(_34){while(_34){if(_34.getAttribute&&_34.getAttribute("widgetId")){return dijit.registry.byId(_34.getAttribute("widgetId"));}_34=_34.parentNode;}return null;};dijit._tabElements={area:true,button:true,input:true,object:true,select:true,textarea:true};dijit._isElementShown=function(_35){var _36=dojo.style(_35);return (_36.visibility!="hidden")&&(_36.visibility!="collapsed")&&(_36.display!="none");};dijit.isTabNavigable=function(_37){if(dojo.hasAttr(_37,"disabled")){return false;}var _38=dojo.hasAttr(_37,"tabindex");var _39=dojo.attr(_37,"tabindex");if(_38&&_39>=0){return true;}var _3a=_37.nodeName.toLowerCase();if(((_3a=="a"&&dojo.hasAttr(_37,"href"))||dijit._tabElements[_3a])&&(!_38||_39>=0)){return true;}return false;};dijit._getTabNavigable=function(_3b){var _3c,_3d,_3e,_3f,_40,_41;var _42=function(_43){dojo.query("> *",_43).forEach(function(_44){var _45=dijit._isElementShown(_44);if(_45&&dijit.isTabNavigable(_44)){var _46=dojo.attr(_44,"tabindex");if(!dojo.hasAttr(_44,"tabindex")||_46==0){if(!_3c){_3c=_44;}_3d=_44;}else{if(_46>0){if(!_3e||_46<_3f){_3f=_46;_3e=_44;}if(!_40||_46>=_41){_41=_46;_40=_44;}}}}if(_45){_42(_44);}});};if(dijit._isElementShown(_3b)){_42(_3b);}return {first:_3c,last:_3d,lowest:_3e,highest:_40};};dijit.getFirstInTabbingOrder=function(_47){var _48=dijit._getTabNavigable(dojo.byId(_47));return _48.lowest?_48.lowest:_48.first;};dijit.getLastInTabbingOrder=function(_49){var _4a=dijit._getTabNavigable(dojo.byId(_49));return _4a.last?_4a.last:_4a.highest;};}if(!dojo._hasResource["dijit._base.place"]){dojo._hasResource["dijit._base.place"]=true;dojo.provide("dijit._base.place");dijit.getViewport=function(){var _4b=dojo.global;var _4c=dojo.doc;var w=0,h=0;var de=_4c.documentElement;var dew=de.clientWidth,deh=de.clientHeight;if(dojo.isMozilla){var _52,_53,_54,_55;var dbw=_4c.body.clientWidth;if(dbw>dew){_52=dew;_54=dbw;}else{_54=dew;_52=dbw;}var dbh=_4c.body.clientHeight;if(dbh>deh){_53=deh;_55=dbh;}else{_55=deh;_53=dbh;}w=(_54>_4b.innerWidth)?_52:_54;h=(_55>_4b.innerHeight)?_53:_55;}else{if(!dojo.isOpera&&_4b.innerWidth){w=_4b.innerWidth;h=_4b.innerHeight;}else{if(dojo.isIE&&de&&deh){w=dew;h=deh;}else{if(dojo.body().clientWidth){w=dojo.body().clientWidth;h=dojo.body().clientHeight;}}}}var _58=dojo._docScroll();return {w:w,h:h,l:_58.x,t:_58.y};};dijit.placeOnScreen=function(_59,pos,_5b,_5c){var _5d=dojo.map(_5b,function(_5e){return {corner:_5e,pos:pos};});return dijit._place(_59,_5d);};dijit._place=function(_5f,_60,_61){var _62=dijit.getViewport();if(!_5f.parentNode||String(_5f.parentNode.tagName).toLowerCase()!="body"){dojo.body().appendChild(_5f);}var _63=null;dojo.some(_60,function(_64){var _65=_64.corner;var pos=_64.pos;if(_61){_61(_5f,_64.aroundCorner,_65);}var _67=_5f.style;var _68=_67.display;var _69=_67.visibility;_67.visibility="hidden";_67.display="";var mb=dojo.marginBox(_5f);_67.display=_68;_67.visibility=_69;var _6b=(_65.charAt(1)=="L"?pos.x:Math.max(_62.l,pos.x-mb.w)),_6c=(_65.charAt(0)=="T"?pos.y:Math.max(_62.t,pos.y-mb.h)),_6d=(_65.charAt(1)=="L"?Math.min(_62.l+_62.w,_6b+mb.w):pos.x),_6e=(_65.charAt(0)=="T"?Math.min(_62.t+_62.h,_6c+mb.h):pos.y),_6f=_6d-_6b,_70=_6e-_6c,_71=(mb.w-_6f)+(mb.h-_70);if(_63==null||_71<_63.overflow){_63={corner:_65,aroundCorner:_64.aroundCorner,x:_6b,y:_6c,w:_6f,h:_70,overflow:_71};}return !_71;});_5f.style.left=_63.x+"px";_5f.style.top=_63.y+"px";if(_63.overflow&&_61){_61(_5f,_63.aroundCorner,_63.corner);}return _63;};dijit.placeOnScreenAroundElement=function(_72,_73,_74,_75){_73=dojo.byId(_73);var _76=_73.style.display;_73.style.display="";var _77=_73.offsetWidth;var _78=_73.offsetHeight;var _79=dojo.coords(_73,true);_73.style.display=_76;var _7a=[];for(var _7b in _74){_7a.push({aroundCorner:_7b,corner:_74[_7b],pos:{x:_79.x+(_7b.charAt(1)=="L"?0:_77),y:_79.y+(_7b.charAt(0)=="T"?0:_78)}});}return dijit._place(_72,_7a,_75);};}if(!dojo._hasResource["dijit._base.window"]){dojo._hasResource["dijit._base.window"]=true;dojo.provide("dijit._base.window");dijit.getDocumentWindow=function(doc){if(dojo.isSafari&&!doc._parentWindow){var fix=function(win){win.document._parentWindow=win;for(var i=0;i<win.frames.length;i++){fix(win.frames[i]);}};fix(window.top);}if(dojo.isIE&&window!==document.parentWindow&&!doc._parentWindow){doc.parentWindow.execScript("document._parentWindow = window;","Javascript");var win=doc._parentWindow;doc._parentWindow=null;return win;}return doc._parentWindow||doc.parentWindow||doc.defaultView;};}if(!dojo._hasResource["dijit._base.popup"]){dojo._hasResource["dijit._base.popup"]=true;dojo.provide("dijit._base.popup");dijit.popup=new function(){var _81=[],_82=1000,_83=1;this.prepare=function(_84){dojo.body().appendChild(_84);var s=_84.style;if(s.display=="none"){s.display="";}s.visibility="hidden";s.position="absolute";s.top="-9999px";};this.open=function(_86){var _87=_86.popup,_88=_86.orient||{"BL":"TL","TL":"BL"},_89=_86.around,id=(_86.around&&_86.around.id)?(_86.around.id+"_dropdown"):("popup_"+_83++);var _8b=dojo.doc.createElement("div");dijit.setWaiRole(_8b,"presentation");_8b.id=id;_8b.className="dijitPopup";_8b.style.zIndex=_82+_81.length;_8b.style.visibility="hidden";if(_86.parent){_8b.dijitPopupParent=_86.parent.id;}dojo.body().appendChild(_8b);var s=_87.domNode.style;s.display="";s.visibility="";s.position="";_8b.appendChild(_87.domNode);var _8d=new dijit.BackgroundIframe(_8b);var _8e=_89?dijit.placeOnScreenAroundElement(_8b,_89,_88,_87.orient?dojo.hitch(_87,"orient"):null):dijit.placeOnScreen(_8b,_86,_88=="R"?["TR","BR","TL","BL"]:["TL","BL","TR","BR"]);_8b.style.visibility="visible";var _8f=[];var _90=function(){for(var pi=_81.length-1;pi>0&&_81[pi].parent===_81[pi-1].widget;pi--){}return _81[pi];};_8f.push(dojo.connect(_8b,"onkeypress",this,function(evt){if(evt.keyCode==dojo.keys.ESCAPE&&_86.onCancel){dojo.stopEvent(evt);_86.onCancel();}else{if(evt.keyCode==dojo.keys.TAB){dojo.stopEvent(evt);var _93=_90();if(_93&&_93.onCancel){_93.onCancel();}}}}));if(_87.onCancel){_8f.push(dojo.connect(_87,"onCancel",null,_86.onCancel));}_8f.push(dojo.connect(_87,_87.onExecute?"onExecute":"onChange",null,function(){var _94=_90();if(_94&&_94.onExecute){_94.onExecute();}}));_81.push({wrapper:_8b,iframe:_8d,widget:_87,parent:_86.parent,onExecute:_86.onExecute,onCancel:_86.onCancel,onClose:_86.onClose,handlers:_8f});if(_87.onOpen){_87.onOpen(_8e);}return _8e;};this.close=function(_95){while(dojo.some(_81,function(_96){return _96.widget==_95;})){var top=_81.pop(),_98=top.wrapper,_99=top.iframe,_9a=top.widget,_9b=top.onClose;if(_9a.onClose){_9a.onClose();}dojo.forEach(top.handlers,dojo.disconnect);if(!_9a||!_9a.domNode){return;}this.prepare(_9a.domNode);_99.destroy();dojo._destroyElement(_98);if(_9b){_9b();}}};}();dijit._frames=new function(){var _9c=[];this.pop=function(){var _9d;if(_9c.length){_9d=_9c.pop();_9d.style.display="";}else{if(dojo.isIE){var _9e="<iframe src='javascript:\"\"'"+" style='position: absolute; left: 0px; top: 0px;"+"z-index: -1; filter:Alpha(Opacity=\"0\");'>";_9d=dojo.doc.createElement(_9e);}else{_9d=dojo.doc.createElement("iframe");_9d.src="javascript:\"\"";_9d.className="dijitBackgroundIframe";}_9d.tabIndex=-1;dojo.body().appendChild(_9d);}return _9d;};this.push=function(_9f){_9f.style.display="";if(dojo.isIE){_9f.style.removeExpression("width");_9f.style.removeExpression("height");}_9c.push(_9f);};}();if(dojo.isIE&&dojo.isIE<7){dojo.addOnLoad(function(){var f=dijit._frames;dojo.forEach([f.pop()],f.push);});}dijit.BackgroundIframe=function(_a1){if(!_a1.id){throw new Error("no id");}if((dojo.isIE&&dojo.isIE<7)||(dojo.isFF&&dojo.isFF<3&&dojo.hasClass(dojo.body(),"dijit_a11y"))){var _a2=dijit._frames.pop();_a1.appendChild(_a2);if(dojo.isIE){_a2.style.setExpression("width",dojo._scopeName+".doc.getElementById('"+_a1.id+"').offsetWidth");_a2.style.setExpression("height",dojo._scopeName+".doc.getElementById('"+_a1.id+"').offsetHeight");}this.iframe=_a2;}};dojo.extend(dijit.BackgroundIframe,{destroy:function(){if(this.iframe){dijit._frames.push(this.iframe);delete this.iframe;}}});}if(!dojo._hasResource["dijit._base.scroll"]){dojo._hasResource["dijit._base.scroll"]=true;dojo.provide("dijit._base.scroll");dijit.scrollIntoView=function(_a3){var _a4=_a3.parentNode;var _a5=_a4.scrollTop+dojo.marginBox(_a4).h;var _a6=_a3.offsetTop+dojo.marginBox(_a3).h;if(_a5<_a6){_a4.scrollTop+=(_a6-_a5);}else{if(_a4.scrollTop>_a3.offsetTop){_a4.scrollTop-=(_a4.scrollTop-_a3.offsetTop);}}};}if(!dojo._hasResource["dijit._base.sniff"]){dojo._hasResource["dijit._base.sniff"]=true;dojo.provide("dijit._base.sniff");(function(){var d=dojo;var ie=d.isIE;var _a9=d.isOpera;var maj=Math.floor;var ff=d.isFF;var _ac={dj_ie:ie,dj_ie6:maj(ie)==6,dj_ie7:maj(ie)==7,dj_iequirks:ie&&d.isQuirks,dj_opera:_a9,dj_opera8:maj(_a9)==8,dj_opera9:maj(_a9)==9,dj_khtml:d.isKhtml,dj_safari:d.isSafari,dj_gecko:d.isMozilla,dj_ff2:maj(ff)==2};for(var p in _ac){if(_ac[p]){var _ae=dojo.doc.documentElement;if(_ae.className){_ae.className+=" "+p;}else{_ae.className=p;}}}})();}if(!dojo._hasResource["dijit._base.bidi"]){dojo._hasResource["dijit._base.bidi"]=true;dojo.provide("dijit._base.bidi");dojo.addOnLoad(function(){if(!dojo._isBodyLtr()){dojo.addClass(dojo.body(),"dijitRtl");}});}if(!dojo._hasResource["dijit._base.typematic"]){dojo._hasResource["dijit._base.typematic"]=true;dojo.provide("dijit._base.typematic");dijit.typematic={_fireEventAndReload:function(){this._timer=null;this._callback(++this._count,this._node,this._evt);this._currentTimeout=(this._currentTimeout<0)?this._initialDelay:((this._subsequentDelay>1)?this._subsequentDelay:Math.round(this._currentTimeout*this._subsequentDelay));this._timer=setTimeout(dojo.hitch(this,"_fireEventAndReload"),this._currentTimeout);},trigger:function(evt,_b0,_b1,_b2,obj,_b4,_b5){if(obj!=this._obj){this.stop();this._initialDelay=_b5||500;this._subsequentDelay=_b4||0.9;this._obj=obj;this._evt=evt;this._node=_b1;this._currentTimeout=-1;this._count=-1;this._callback=dojo.hitch(_b0,_b2);this._fireEventAndReload();}},stop:function(){if(this._timer){clearTimeout(this._timer);this._timer=null;}if(this._obj){this._callback(-1,this._node,this._evt);this._obj=null;}},addKeyListener:function(_b6,_b7,_b8,_b9,_ba,_bb){return [dojo.connect(_b6,"onkeypress",this,function(evt){if(evt.keyCode==_b7.keyCode&&(!_b7.charCode||_b7.charCode==evt.charCode)&&(_b7.ctrlKey===undefined||_b7.ctrlKey==evt.ctrlKey)&&(_b7.altKey===undefined||_b7.altKey==evt.ctrlKey)&&(_b7.shiftKey===undefined||_b7.shiftKey==evt.ctrlKey)){dojo.stopEvent(evt);dijit.typematic.trigger(_b7,_b8,_b6,_b9,_b7,_ba,_bb);}else{if(dijit.typematic._obj==_b7){dijit.typematic.stop();}}}),dojo.connect(_b6,"onkeyup",this,function(evt){if(dijit.typematic._obj==_b7){dijit.typematic.stop();}})];},addMouseListener:function(_be,_bf,_c0,_c1,_c2){var dc=dojo.connect;return [dc(_be,"mousedown",this,function(evt){dojo.stopEvent(evt);dijit.typematic.trigger(evt,_bf,_be,_c0,_be,_c1,_c2);}),dc(_be,"mouseup",this,function(evt){dojo.stopEvent(evt);dijit.typematic.stop();}),dc(_be,"mouseout",this,function(evt){dojo.stopEvent(evt);dijit.typematic.stop();}),dc(_be,"mousemove",this,function(evt){dojo.stopEvent(evt);}),dc(_be,"dblclick",this,function(evt){dojo.stopEvent(evt);if(dojo.isIE){dijit.typematic.trigger(evt,_bf,_be,_c0,_be,_c1,_c2);setTimeout(dojo.hitch(this,dijit.typematic.stop),50);}})];},addListener:function(_c9,_ca,_cb,_cc,_cd,_ce,_cf){return this.addKeyListener(_ca,_cb,_cc,_cd,_ce,_cf).concat(this.addMouseListener(_c9,_cc,_cd,_ce,_cf));}};}if(!dojo._hasResource["dijit._base.wai"]){dojo._hasResource["dijit._base.wai"]=true;dojo.provide("dijit._base.wai");dijit.wai={onload:function(){var div=dojo.doc.createElement("div");div.id="a11yTestNode";div.style.cssText="border: 1px solid;"+"border-color:red green;"+"position: absolute;"+"height: 5px;"+"top: -999px;"+"background-image: url(\""+dojo.moduleUrl("dojo","resources/blank.gif")+"\");";dojo.body().appendChild(div);var cs=dojo.getComputedStyle(div);if(cs){var _d2=cs.backgroundImage;var _d3=(cs.borderTopColor==cs.borderRightColor)||(_d2!=null&&(_d2=="none"||_d2=="url(invalid-url:)"));dojo[_d3?"addClass":"removeClass"](dojo.body(),"dijit_a11y");dojo.body().removeChild(div);}}};if(dojo.isIE||dojo.isMoz){dojo._loaders.unshift(dijit.wai.onload);}dojo.mixin(dijit,{hasWaiRole:function(_d4){return _d4.hasAttribute?_d4.hasAttribute("role"):!!_d4.getAttribute("role");},getWaiRole:function(_d5){var _d6=_d5.getAttribute("role");if(_d6){var _d7=_d6.indexOf(":");return _d7==-1?_d6:_d6.substring(_d7+1);}else{return "";}},setWaiRole:function(_d8,_d9){_d8.setAttribute("role",(dojo.isFF&&dojo.isFF<3)?"wairole:"+_d9:_d9);},removeWaiRole:function(_da){_da.removeAttribute("role");},hasWaiState:function(_db,_dc){if(dojo.isFF&&dojo.isFF<3){return _db.hasAttributeNS("http://www.w3.org/2005/07/aaa",_dc);}else{return _db.hasAttribute?_db.hasAttribute("aria-"+_dc):!!_db.getAttribute("aria-"+_dc);}},getWaiState:function(_dd,_de){if(dojo.isFF&&dojo.isFF<3){return _dd.getAttributeNS("http://www.w3.org/2005/07/aaa",_de);}else{var _df=_dd.getAttribute("aria-"+_de);return _df?_df:"";}},setWaiState:function(_e0,_e1,_e2){if(dojo.isFF&&dojo.isFF<3){_e0.setAttributeNS("http://www.w3.org/2005/07/aaa","aaa:"+_e1,_e2);}else{_e0.setAttribute("aria-"+_e1,_e2);}},removeWaiState:function(_e3,_e4){if(dojo.isFF&&dojo.isFF<3){_e3.removeAttributeNS("http://www.w3.org/2005/07/aaa",_e4);}else{_e3.removeAttribute("aria-"+_e4);}}});}if(!dojo._hasResource["dijit._base"]){dojo._hasResource["dijit._base"]=true;dojo.provide("dijit._base");if(dojo.isSafari){dojo.connect(window,"load",function(){window.resizeBy(1,0);setTimeout(function(){window.resizeBy(-1,0);},10);});}}if(!dojo._hasResource["dojo.date.stamp"]){dojo._hasResource["dojo.date.stamp"]=true;dojo.provide("dojo.date.stamp");dojo.date.stamp.fromISOString=function(_e5,_e6){if(!dojo.date.stamp._isoRegExp){dojo.date.stamp._isoRegExp=/^(?:(\d{4})(?:-(\d{2})(?:-(\d{2}))?)?)?(?:T(\d{2}):(\d{2})(?::(\d{2})(.\d+)?)?((?:[+-](\d{2}):(\d{2}))|Z)?)?$/;}var _e7=dojo.date.stamp._isoRegExp.exec(_e5);var _e8=null;if(_e7){_e7.shift();if(_e7[1]){_e7[1]--;}if(_e7[6]){_e7[6]*=1000;}if(_e6){_e6=new Date(_e6);dojo.map(["FullYear","Month","Date","Hours","Minutes","Seconds","Milliseconds"],function(_e9){return _e6["get"+_e9]();}).forEach(function(_ea,_eb){if(_e7[_eb]===undefined){_e7[_eb]=_ea;}});}_e8=new Date(_e7[0]||1970,_e7[1]||0,_e7[2]||1,_e7[3]||0,_e7[4]||0,_e7[5]||0,_e7[6]||0);var _ec=0;var _ed=_e7[7]&&_e7[7].charAt(0);if(_ed!="Z"){_ec=((_e7[8]||0)*60)+(Number(_e7[9])||0);if(_ed!="-"){_ec*=-1;}}if(_ed){_ec-=_e8.getTimezoneOffset();}if(_ec){_e8.setTime(_e8.getTime()+_ec*60000);}}return _e8;};dojo.date.stamp.toISOString=function(_ee,_ef){var _=function(n){return (n<10)?"0"+n:n;};_ef=_ef||{};var _f2=[];var _f3=_ef.zulu?"getUTC":"get";var _f4="";if(_ef.selector!="time"){var _f5=_ee[_f3+"FullYear"]();_f4=["0000".substr((_f5+"").length)+_f5,_(_ee[_f3+"Month"]()+1),_(_ee[_f3+"Date"]())].join("-");}_f2.push(_f4);if(_ef.selector!="date"){var _f6=[_(_ee[_f3+"Hours"]()),_(_ee[_f3+"Minutes"]()),_(_ee[_f3+"Seconds"]())].join(":");var _f7=_ee[_f3+"Milliseconds"]();if(_ef.milliseconds){_f6+="."+(_f7<100?"0":"")+_(_f7);}if(_ef.zulu){_f6+="Z";}else{if(_ef.selector!="time"){var _f8=_ee.getTimezoneOffset();var _f9=Math.abs(_f8);_f6+=(_f8>0?"-":"+")+_(Math.floor(_f9/60))+":"+_(_f9%60);}}_f2.push(_f6);}return _f2.join("T");};}if(!dojo._hasResource["dojo.parser"]){dojo._hasResource["dojo.parser"]=true;dojo.provide("dojo.parser");dojo.parser=new function(){var d=dojo;var _fb=d._scopeName+"Type";var qry="["+_fb+"]";function val2type(_fd){if(d.isString(_fd)){return "string";}if(typeof _fd=="number"){return "number";}if(typeof _fd=="boolean"){return "boolean";}if(d.isFunction(_fd)){return "function";}if(d.isArray(_fd)){return "array";}if(_fd instanceof Date){return "date";}if(_fd instanceof d._Url){return "url";}return "object";};function str2obj(_fe,_ff){switch(_ff){case "string":return _fe;case "number":return _fe.length?Number(_fe):NaN;case "boolean":return typeof _fe=="boolean"?_fe:!(_fe.toLowerCase()=="false");case "function":if(d.isFunction(_fe)){_fe=_fe.toString();_fe=d.trim(_fe.substring(_fe.indexOf("{")+1,_fe.length-1));}try{if(_fe.search(/[^\w\.]+/i)!=-1){_fe=d.parser._nameAnonFunc(new Function(_fe),this);}return d.getObject(_fe,false);}catch(e){return new Function();}case "array":return _fe.split(/\s*,\s*/);case "date":switch(_fe){case "":return new Date("");case "now":return new Date();default:return d.date.stamp.fromISOString(_fe);}case "url":return d.baseUrl+_fe;default:return d.fromJson(_fe);}};var _100={};function getClassInfo(_101){if(!_100[_101]){var cls=d.getObject(_101);if(!d.isFunction(cls)){throw new Error("Could not load class '"+_101+"'. Did you spell the name correctly and use a full path, like 'dijit.form.Button'?");}var _103=cls.prototype;var _104={};for(var name in _103){if(name.charAt(0)=="_"){continue;}var _106=_103[name];_104[name]=val2type(_106);}_100[_101]={cls:cls,params:_104};}return _100[_101];};this._functionFromScript=function(_107){var _108="";var _109="";var _10a=_107.getAttribute("args");if(_10a){d.forEach(_10a.split(/\s*,\s*/),function(part,idx){_108+="var "+part+" = arguments["+idx+"]; ";});}var _10d=_107.getAttribute("with");if(_10d&&_10d.length){d.forEach(_10d.split(/\s*,\s*/),function(part){_108+="with("+part+"){";_109+="}";});}return new Function(_108+_107.innerHTML+_109);};this.instantiate=function(_10f){var _110=[];d.forEach(_10f,function(node){if(!node){return;}var type=node.getAttribute(_fb);if((!type)||(!type.length)){return;}var _113=getClassInfo(type);var _114=_113.cls;var ps=_114._noScript||_114.prototype._noScript;var _116={};var _117=node.attributes;for(var name in _113.params){var item=_117.getNamedItem(name);if(!item||(!item.specified&&(!dojo.isIE||name.toLowerCase()!="value"))){continue;}var _11a=item.value;switch(name){case "class":_11a=node.className;break;case "style":_11a=node.style&&node.style.cssText;}var _11b=_113.params[name];_116[name]=str2obj(_11a,_11b);}if(!ps){var _11c=[],_11d=[];d.query("> script[type^='dojo/']",node).orphan().forEach(function(_11e){var _11f=_11e.getAttribute("event"),type=_11e.getAttribute("type"),nf=d.parser._functionFromScript(_11e);if(_11f){if(type=="dojo/connect"){_11c.push({event:_11f,func:nf});}else{_116[_11f]=nf;}}else{_11d.push(nf);}});}var _121=_114["markupFactory"];if(!_121&&_114["prototype"]){_121=_114.prototype["markupFactory"];}var _122=_121?_121(_116,node,_114):new _114(_116,node);_110.push(_122);var _123=node.getAttribute("jsId");if(_123){d.setObject(_123,_122);}if(!ps){d.forEach(_11c,function(_124){d.connect(_122,_124.event,null,_124.func);});d.forEach(_11d,function(func){func.call(_122);});}});d.forEach(_110,function(_126){if(_126&&_126.startup&&!_126._started&&(!_126.getParent||!_126.getParent())){_126.startup();}});return _110;};this.parse=function(_127){var list=d.query(qry,_127);var _129=this.instantiate(list);return _129;};}();(function(){var _12a=function(){if(dojo.config["parseOnLoad"]==true){dojo.parser.parse();}};if(dojo.exists("dijit.wai.onload")&&(dijit.wai.onload===dojo._loaders[0])){dojo._loaders.splice(1,0,_12a);}else{dojo._loaders.unshift(_12a);}})();dojo.parser._anonCtr=0;dojo.parser._anon={};dojo.parser._nameAnonFunc=function(_12b,_12c){var jpn="$joinpoint";var nso=(_12c||dojo.parser._anon);if(dojo.isIE){var cn=_12b["__dojoNameCache"];if(cn&&nso[cn]===_12b){return _12b["__dojoNameCache"];}}var ret="__"+dojo.parser._anonCtr++;while(typeof nso[ret]!="undefined"){ret="__"+dojo.parser._anonCtr++;}nso[ret]=_12b;return ret;};}if(!dojo._hasResource["dijit._Widget"]){dojo._hasResource["dijit._Widget"]=true;dojo.provide("dijit._Widget");dojo.require("dijit._base");dojo.declare("dijit._Widget",null,{id:"",lang:"",dir:"","class":"",style:"",title:"",srcNodeRef:null,domNode:null,attributeMap:{id:"",dir:"",lang:"","class":"",style:"",title:""},postscript:function(_131,_132){this.create(_131,_132);},create:function(_133,_134){this.srcNodeRef=dojo.byId(_134);this._connects=[];this._attaches=[];if(this.srcNodeRef&&(typeof this.srcNodeRef.id=="string")){this.id=this.srcNodeRef.id;}if(_133){this.params=_133;dojo.mixin(this,_133);}this.postMixInProperties();if(!this.id){this.id=dijit.getUniqueId(this.declaredClass.replace(/\./g,"_"));}dijit.registry.add(this);this.buildRendering();if(this.domNode){for(var attr in this.attributeMap){var _136=this[attr];if(typeof _136!="object"&&((_136!==""&&_136!==false)||(_133&&_133[attr]))){this.setAttribute(attr,_136);}}}if(this.domNode){this.domNode.setAttribute("widgetId",this.id);}this.postCreate();if(this.srcNodeRef&&!this.srcNodeRef.parentNode){delete this.srcNodeRef;}},postMixInProperties:function(){},buildRendering:function(){this.domNode=this.srcNodeRef||dojo.doc.createElement("div");},postCreate:function(){},startup:function(){this._started=true;},destroyRecursive:function(_137){this.destroyDescendants();this.destroy();},destroy:function(_138){this.uninitialize();dojo.forEach(this._connects,function(_139){dojo.forEach(_139,dojo.disconnect);});dojo.forEach(this._supportingWidgets||[],function(w){w.destroy();});this.destroyRendering(_138);dijit.registry.remove(this.id);},destroyRendering:function(_13b){if(this.bgIframe){this.bgIframe.destroy();delete this.bgIframe;}if(this.domNode){dojo._destroyElement(this.domNode);delete this.domNode;}if(this.srcNodeRef){dojo._destroyElement(this.srcNodeRef);delete this.srcNodeRef;}},destroyDescendants:function(){dojo.forEach(this.getDescendants(),function(_13c){_13c.destroy();});},uninitialize:function(){return false;},onFocus:function(){},onBlur:function(){},_onFocus:function(e){this.onFocus();},_onBlur:function(){this.onBlur();},setAttribute:function(attr,_13f){var _140=this[this.attributeMap[attr]||"domNode"];this[attr]=_13f;switch(attr){case "class":dojo.addClass(_140,_13f);break;case "style":if(_140.style.cssText){_140.style.cssText+="; "+_13f;}else{_140.style.cssText=_13f;}break;default:if(/^on[A-Z]/.test(attr)){attr=attr.toLowerCase();}if(typeof _13f=="function"){_13f=dojo.hitch(this,_13f);}dojo.attr(_140,attr,_13f);}},toString:function(){return "[Widget "+this.declaredClass+", "+(this.id||"NO ID")+"]";},getDescendants:function(){if(this.containerNode){var list=dojo.query("[widgetId]",this.containerNode);return list.map(dijit.byNode);}else{return [];}},nodesWithKeyClick:["input","button"],connect:function(obj,_143,_144){var _145=[];if(_143=="ondijitclick"){if(!this.nodesWithKeyClick[obj.nodeName]){_145.push(dojo.connect(obj,"onkeydown",this,function(e){if(e.keyCode==dojo.keys.ENTER){return (dojo.isString(_144))?this[_144](e):_144.call(this,e);}else{if(e.keyCode==dojo.keys.SPACE){dojo.stopEvent(e);}}}));_145.push(dojo.connect(obj,"onkeyup",this,function(e){if(e.keyCode==dojo.keys.SPACE){return dojo.isString(_144)?this[_144](e):_144.call(this,e);}}));}_143="onclick";}_145.push(dojo.connect(obj,_143,this,_144));this._connects.push(_145);return _145;},disconnect:function(_148){for(var i=0;i<this._connects.length;i++){if(this._connects[i]==_148){dojo.forEach(_148,dojo.disconnect);this._connects.splice(i,1);return;}}},isLeftToRight:function(){if(!("_ltr" in this)){this._ltr=dojo.getComputedStyle(this.domNode).direction!="rtl";}return this._ltr;},isFocusable:function(){return this.focus&&(dojo.style(this.domNode,"display")!="none");}});}if(!dojo._hasResource["dojo.string"]){dojo._hasResource["dojo.string"]=true;dojo.provide("dojo.string");dojo.string.pad=function(text,size,ch,end){var out=String(text);if(!ch){ch="0";}while(out.length<size){if(end){out+=ch;}else{out=ch+out;}}return out;};dojo.string.substitute=function(_14f,map,_151,_152){return _14f.replace(/\$\{([^\s\:\}]+)(?:\:([^\s\:\}]+))?\}/g,function(_153,key,_155){var _156=dojo.getObject(key,false,map);if(_155){_156=dojo.getObject(_155,false,_152)(_156);}if(_151){_156=_151(_156,key);}return _156.toString();});};dojo.string.trim=function(str){str=str.replace(/^\s+/,"");for(var i=str.length-1;i>0;i--){if(/\S/.test(str.charAt(i))){str=str.substring(0,i+1);break;}}return str;};}if(!dojo._hasResource["dijit._Templated"]){dojo._hasResource["dijit._Templated"]=true;dojo.provide("dijit._Templated");dojo.declare("dijit._Templated",null,{templateNode:null,templateString:null,templatePath:null,widgetsInTemplate:false,containerNode:null,_skipNodeCache:false,_stringRepl:function(tmpl){var _15a=this.declaredClass,_15b=this;return dojo.string.substitute(tmpl,this,function(_15c,key){if(key.charAt(0)=="!"){_15c=_15b[key.substr(1)];}if(typeof _15c=="undefined"){throw new Error(_15a+" template:"+key);}if(!_15c){return "";}return key.charAt(0)=="!"?_15c:_15c.toString().replace(/"/g,""");},this);},buildRendering:function(){var _15e=dijit._Templated.getCachedTemplate(this.templatePath,this.templateString,this._skipNodeCache);var node;if(dojo.isString(_15e)){node=dijit._Templated._createNodesFromText(this._stringRepl(_15e))[0];}else{node=_15e.cloneNode(true);}this._attachTemplateNodes(node);var _160=this.srcNodeRef;if(_160&&_160.parentNode){_160.parentNode.replaceChild(node,_160);}this.domNode=node;if(this.widgetsInTemplate){var cw=this._supportingWidgets=dojo.parser.parse(node);this._attachTemplateNodes(cw,function(n,p){return n[p];});}this._fillContent(_160);},_fillContent:function(_164){var dest=this.containerNode;if(_164&&dest){while(_164.hasChildNodes()){dest.appendChild(_164.firstChild);}}},_attachTemplateNodes:function(_166,_167){_167=_167||function(n,p){return n.getAttribute(p);};var _16a=dojo.isArray(_166)?_166:(_166.all||_166.getElementsByTagName("*"));var x=dojo.isArray(_166)?0:-1;for(;x<_16a.length;x++){var _16c=(x==-1)?_166:_16a[x];if(this.widgetsInTemplate&&_167(_16c,"dojoType")){continue;}var _16d=_167(_16c,"dojoAttachPoint");if(_16d){var _16e,_16f=_16d.split(/\s*,\s*/);while((_16e=_16f.shift())){if(dojo.isArray(this[_16e])){this[_16e].push(_16c);}else{this[_16e]=_16c;}}}var _170=_167(_16c,"dojoAttachEvent");if(_170){var _171,_172=_170.split(/\s*,\s*/);var trim=dojo.trim;while((_171=_172.shift())){if(_171){var _174=null;if(_171.indexOf(":")!=-1){var _175=_171.split(":");_171=trim(_175[0]);_174=trim(_175[1]);}else{_171=trim(_171);}if(!_174){_174=_171;}this.connect(_16c,_171,_174);}}}var role=_167(_16c,"waiRole");if(role){dijit.setWaiRole(_16c,role);}var _177=_167(_16c,"waiState");if(_177){dojo.forEach(_177.split(/\s*,\s*/),function(_178){if(_178.indexOf("-")!=-1){var pair=_178.split("-");dijit.setWaiState(_16c,pair[0],pair[1]);}});}}}});dijit._Templated._templateCache={};dijit._Templated.getCachedTemplate=function(_17a,_17b,_17c){var _17d=dijit._Templated._templateCache;var key=_17b||_17a;var _17f=_17d[key];if(_17f){return _17f;}if(!_17b){_17b=dijit._Templated._sanitizeTemplateString(dojo._getText(_17a));}_17b=dojo.string.trim(_17b);if(_17c||_17b.match(/\$\{([^\}]+)\}/g)){return (_17d[key]=_17b);}else{return (_17d[key]=dijit._Templated._createNodesFromText(_17b)[0]);}};dijit._Templated._sanitizeTemplateString=function(_180){if(_180){_180=_180.replace(/^\s*<\?xml(\s)+version=[\'\"](\d)*.(\d)*[\'\"](\s)*\?>/im,"");var _181=_180.match(/<body[^>]*>\s*([\s\S]+)\s*<\/body>/im);if(_181){_180=_181[1];}}else{_180="";}return _180;};if(dojo.isIE){dojo.addOnUnload(function(){var _182=dijit._Templated._templateCache;for(var key in _182){var _184=_182[key];if(!isNaN(_184.nodeType)){dojo._destroyElement(_184);}delete _182[key];}});}(function(){var _185={cell:{re:/^<t[dh][\s\r\n>]/i,pre:"<table><tbody><tr>",post:"</tr></tbody></table>"},row:{re:/^<tr[\s\r\n>]/i,pre:"<table><tbody>",post:"</tbody></table>"},section:{re:/^<(thead|tbody|tfoot)[\s\r\n>]/i,pre:"<table>",post:"</table>"}};var tn;dijit._Templated._createNodesFromText=function(text){if(!tn){tn=dojo.doc.createElement("div");tn.style.display="none";dojo.body().appendChild(tn);}var _188="none";var _189=text.replace(/^\s+/,"");for(var type in _185){var map=_185[type];if(map.re.test(_189)){_188=type;text=map.pre+text+map.post;break;}}tn.innerHTML=text;if(tn.normalize){tn.normalize();}var tag={cell:"tr",row:"tbody",section:"table"}[_188];var _18d=(typeof tag!="undefined")?tn.getElementsByTagName(tag)[0]:tn;var _18e=[];while(_18d.firstChild){_18e.push(_18d.removeChild(_18d.firstChild));}tn.innerHTML="";return _18e;};})();dojo.extend(dijit._Widget,{dojoAttachEvent:"",dojoAttachPoint:"",waiRole:"",waiState:""});}if(!dojo._hasResource["dijit._Container"]){dojo._hasResource["dijit._Container"]=true;dojo.provide("dijit._Container");dojo.declare("dijit._Contained",null,{getParent:function(){for(var p=this.domNode.parentNode;p;p=p.parentNode){var id=p.getAttribute&&p.getAttribute("widgetId");if(id){var _191=dijit.byId(id);return _191.isContainer?_191:null;}}return null;},_getSibling:function(_192){var node=this.domNode;do{node=node[_192+"Sibling"];}while(node&&node.nodeType!=1);if(!node){return null;}var id=node.getAttribute("widgetId");return dijit.byId(id);},getPreviousSibling:function(){return this._getSibling("previous");},getNextSibling:function(){return this._getSibling("next");}});dojo.declare("dijit._Container",null,{isContainer:true,addChild:function(_195,_196){if(_196===undefined){_196="last";}var _197=this.containerNode||this.domNode;if(_196&&typeof _196=="number"){var _198=dojo.query("> [widgetid]",_197);if(_198&&_198.length>=_196){_197=_198[_196-1];_196="after";}}dojo.place(_195.domNode,_197,_196);if(this._started&&!_195._started){_195.startup();}},removeChild:function(_199){var node=_199.domNode;node.parentNode.removeChild(node);},_nextElement:function(node){do{node=node.nextSibling;}while(node&&node.nodeType!=1);return node;},_firstElement:function(node){node=node.firstChild;if(node&&node.nodeType!=1){node=this._nextElement(node);}return node;},getChildren:function(){return dojo.query("> [widgetId]",this.containerNode||this.domNode).map(dijit.byNode);},hasChildren:function(){var cn=this.containerNode||this.domNode;return !!this._firstElement(cn);},_getSiblingOfChild:function(_19e,dir){var node=_19e.domNode;var _1a1=(dir>0?"nextSibling":"previousSibling");do{node=node[_1a1];}while(node&&(node.nodeType!=1||!dijit.byNode(node)));return node?dijit.byNode(node):null;}});dojo.declare("dijit._KeyNavContainer",[dijit._Container],{_keyNavCodes:{},connectKeyNavHandlers:function(_1a2,_1a3){var _1a4=this._keyNavCodes={};var prev=dojo.hitch(this,this.focusPrev);var next=dojo.hitch(this,this.focusNext);dojo.forEach(_1a2,function(code){_1a4[code]=prev;});dojo.forEach(_1a3,function(code){_1a4[code]=next;});this.connect(this.domNode,"onkeypress","_onContainerKeypress");this.connect(this.domNode,"onfocus","_onContainerFocus");},startupKeyNavChildren:function(){dojo.forEach(this.getChildren(),dojo.hitch(this,"_startupChild"));},addChild:function(_1a9,_1aa){dijit._KeyNavContainer.superclass.addChild.apply(this,arguments);this._startupChild(_1a9);},focus:function(){this.focusFirstChild();},focusFirstChild:function(){this.focusChild(this._getFirstFocusableChild());},focusNext:function(){if(this.focusedChild&&this.focusedChild.hasNextFocalNode&&this.focusedChild.hasNextFocalNode()){this.focusedChild.focusNext();return;}var _1ab=this._getNextFocusableChild(this.focusedChild,1);if(_1ab.getFocalNodes){this.focusChild(_1ab,_1ab.getFocalNodes()[0]);}else{this.focusChild(_1ab);}},focusPrev:function(){if(this.focusedChild&&this.focusedChild.hasPrevFocalNode&&this.focusedChild.hasPrevFocalNode()){this.focusedChild.focusPrev();return;}var _1ac=this._getNextFocusableChild(this.focusedChild,-1);if(_1ac.getFocalNodes){var _1ad=_1ac.getFocalNodes();this.focusChild(_1ac,_1ad[_1ad.length-1]);}else{this.focusChild(_1ac);}},focusChild:function(_1ae,node){if(_1ae){if(this.focusedChild&&_1ae!==this.focusedChild){this._onChildBlur(this.focusedChild);}this.focusedChild=_1ae;if(node&&_1ae.focusFocalNode){_1ae.focusFocalNode(node);}else{_1ae.focus();}}},_startupChild:function(_1b0){if(_1b0.getFocalNodes){dojo.forEach(_1b0.getFocalNodes(),function(node){dojo.attr(node,"tabindex",-1);this._connectNode(node);},this);}else{var node=_1b0.focusNode||_1b0.domNode;if(_1b0.isFocusable()){dojo.attr(node,"tabindex",-1);}this._connectNode(node);}},_connectNode:function(node){this.connect(node,"onfocus","_onNodeFocus");this.connect(node,"onblur","_onNodeBlur");},_onContainerFocus:function(evt){if(evt.target===this.domNode){this.focusFirstChild();}},_onContainerKeypress:function(evt){if(evt.ctrlKey||evt.altKey){return;}var func=this._keyNavCodes[evt.keyCode];if(func){func();dojo.stopEvent(evt);}},_onNodeFocus:function(evt){dojo.attr(this.domNode,"tabindex",-1);var _1b8=dijit.getEnclosingWidget(evt.target);if(_1b8&&_1b8.isFocusable()){this.focusedChild=_1b8;}dojo.stopEvent(evt);},_onNodeBlur:function(evt){if(this.tabIndex){dojo.attr(this.domNode,"tabindex",this.tabIndex);}dojo.stopEvent(evt);},_onChildBlur:function(_1ba){},_getFirstFocusableChild:function(){return this._getNextFocusableChild(null,1);},_getNextFocusableChild:function(_1bb,dir){if(_1bb){_1bb=this._getSiblingOfChild(_1bb,dir);}var _1bd=this.getChildren();for(var i=0;i<_1bd.length;i++){if(!_1bb){_1bb=_1bd[(dir>0)?0:(_1bd.length-1)];}if(_1bb.isFocusable()){return _1bb;}_1bb=this._getSiblingOfChild(_1bb,dir);}return null;}});}if(!dojo._hasResource["dijit.layout._LayoutWidget"]){dojo._hasResource["dijit.layout._LayoutWidget"]=true;dojo.provide("dijit.layout._LayoutWidget");dojo.declare("dijit.layout._LayoutWidget",[dijit._Widget,dijit._Container,dijit._Contained],{isLayoutContainer:true,postCreate:function(){dojo.addClass(this.domNode,"dijitContainer");},startup:function(){if(this._started){return;}dojo.forEach(this.getChildren(),function(_1bf){_1bf.startup();});if(!this.getParent||!this.getParent()){this.resize();this.connect(window,"onresize",function(){this.resize();});}this.inherited(arguments);},resize:function(args){var node=this.domNode;if(args){dojo.marginBox(node,args);if(args.t){node.style.top=args.t+"px";}if(args.l){node.style.left=args.l+"px";}}var mb=dojo.mixin(dojo.marginBox(node),args||{});this._contentBox=dijit.layout.marginBox2contentBox(node,mb);this.layout();},layout:function(){}});dijit.layout.marginBox2contentBox=function(node,mb){var cs=dojo.getComputedStyle(node);var me=dojo._getMarginExtents(node,cs);var pb=dojo._getPadBorderExtents(node,cs);return {l:dojo._toPixelValue(node,cs.paddingLeft),t:dojo._toPixelValue(node,cs.paddingTop),w:mb.w-(me.w+pb.w),h:mb.h-(me.h+pb.h)};};(function(){var _1c8=function(word){return word.substring(0,1).toUpperCase()+word.substring(1);};var size=function(_1cb,dim){_1cb.resize?_1cb.resize(dim):dojo.marginBox(_1cb.domNode,dim);dojo.mixin(_1cb,dojo.marginBox(_1cb.domNode));dojo.mixin(_1cb,dim);};dijit.layout.layoutChildren=function(_1cd,dim,_1cf){dim=dojo.mixin({},dim);dojo.addClass(_1cd,"dijitLayoutContainer");_1cf=dojo.filter(_1cf,function(item){return item.layoutAlign!="client";}).concat(dojo.filter(_1cf,function(item){return item.layoutAlign=="client";}));dojo.forEach(_1cf,function(_1d2){var elm=_1d2.domNode,pos=_1d2.layoutAlign;var _1d5=elm.style;_1d5.left=dim.l+"px";_1d5.top=dim.t+"px";_1d5.bottom=_1d5.right="auto";dojo.addClass(elm,"dijitAlign"+_1c8(pos));if(pos=="top"||pos=="bottom"){size(_1d2,{w:dim.w});dim.h-=_1d2.h;if(pos=="top"){dim.t+=_1d2.h;}else{_1d5.top=dim.t+dim.h+"px";}}else{if(pos=="left"||pos=="right"){size(_1d2,{h:dim.h});dim.w-=_1d2.w;if(pos=="left"){dim.l+=_1d2.w;}else{_1d5.left=dim.l+dim.w+"px";}}else{if(pos=="client"){size(_1d2,dim);}}}});};})();}if(!dojo._hasResource["dijit.form._FormWidget"]){dojo._hasResource["dijit.form._FormWidget"]=true;dojo.provide("dijit.form._FormWidget");dojo.declare("dijit.form._FormWidget",[dijit._Widget,dijit._Templated],{baseClass:"",name:"",alt:"",value:"",type:"text",tabIndex:"0",disabled:false,readOnly:false,intermediateChanges:false,attributeMap:dojo.mixin(dojo.clone(dijit._Widget.prototype.attributeMap),{value:"focusNode",disabled:"focusNode",readOnly:"focusNode",id:"focusNode",tabIndex:"focusNode",alt:"focusNode"}),setAttribute:function(attr,_1d7){this.inherited(arguments);switch(attr){case "disabled":var _1d8=this[this.attributeMap["tabIndex"]||"domNode"];if(_1d7){this._hovering=false;this._active=false;_1d8.removeAttribute("tabIndex");}else{_1d8.setAttribute("tabIndex",this.tabIndex);}dijit.setWaiState(this[this.attributeMap["disabled"]||"domNode"],"disabled",_1d7);this._setStateClass();}},setDisabled:function(_1d9){dojo.deprecated("setDisabled("+_1d9+") is deprecated. Use setAttribute('disabled',"+_1d9+") instead.","","2.0");this.setAttribute("disabled",_1d9);},_onMouse:function(_1da){var _1db=_1da.currentTarget;if(_1db&&_1db.getAttribute){this.stateModifier=_1db.getAttribute("stateModifier")||"";}if(!this.disabled){switch(_1da.type){case "mouseenter":case "mouseover":this._hovering=true;this._active=this._mouseDown;break;case "mouseout":case "mouseleave":this._hovering=false;this._active=false;break;case "mousedown":this._active=true;this._mouseDown=true;var _1dc=this.connect(dojo.body(),"onmouseup",function(){this._active=false;this._mouseDown=false;this._setStateClass();this.disconnect(_1dc);});if(this.isFocusable()){this.focus();}break;}this._setStateClass();}},isFocusable:function(){return !this.disabled&&!this.readOnly&&this.focusNode&&(dojo.style(this.domNode,"display")!="none");},focus:function(){setTimeout(dojo.hitch(this,dijit.focus,this.focusNode),0);},_setStateClass:function(){if(!("staticClass" in this)){this.staticClass=(this.stateNode||this.domNode).className;}var _1dd=[this.baseClass];function multiply(_1de){_1dd=_1dd.concat(dojo.map(_1dd,function(c){return c+_1de;}),"dijit"+_1de);};if(this.checked){multiply("Checked");}if(this.state){multiply(this.state);}if(this.selected){multiply("Selected");}if(this.disabled){multiply("Disabled");}else{if(this.readOnly){multiply("ReadOnly");}else{if(this._active){multiply(this.stateModifier+"Active");}else{if(this._focused){multiply("Focused");}if(this._hovering){multiply(this.stateModifier+"Hover");}}}}(this.stateNode||this.domNode).className=this.staticClass+" "+_1dd.join(" ");},onChange:function(_1e0){},_onChangeMonitor:"value",_onChangeActive:false,_handleOnChange:function(_1e1,_1e2){this._lastValue=_1e1;if(this._lastValueReported==undefined&&(_1e2===null||!this._onChangeActive)){this._resetValue=this._lastValueReported=_1e1;}if((this.intermediateChanges||_1e2||_1e2===undefined)&&((_1e1&&_1e1.toString)?_1e1.toString():_1e1)!==((this._lastValueReported&&this._lastValueReported.toString)?this._lastValueReported.toString():this._lastValueReported)){this._lastValueReported=_1e1;if(this._onChangeActive){this.onChange(_1e1);}}},reset:function(){this._hasBeenBlurred=false;if(this.setValue&&!this._getValueDeprecated){this.setValue(this._resetValue,true);}else{if(this._onChangeMonitor){this.setAttribute(this._onChangeMonitor,(this._resetValue!==undefined&&this._resetValue!==null)?this._resetValue:"");}}},create:function(){this.inherited(arguments);this._onChangeActive=true;this._setStateClass();},destroy:function(){if(this._layoutHackHandle){clearTimeout(this._layoutHackHandle);}this.inherited(arguments);},setValue:function(_1e3){dojo.deprecated("dijit.form._FormWidget:setValue("+_1e3+") is deprecated. Use setAttribute('value',"+_1e3+") instead.","","2.0");this.setAttribute("value",_1e3);},_getValueDeprecated:true,getValue:function(){dojo.deprecated("dijit.form._FormWidget:getValue() is deprecated. Use widget.value instead.","","2.0");return this.value;},_layoutHack:function(){if(dojo.isFF==2){var node=this.domNode;var old=node.style.opacity;node.style.opacity="0.999";this._layoutHackHandle=setTimeout(dojo.hitch(this,function(){this._layoutHackHandle=null;node.style.opacity=old;}),0);}}});dojo.declare("dijit.form._FormValueWidget",dijit.form._FormWidget,{attributeMap:dojo.mixin(dojo.clone(dijit.form._FormWidget.prototype.attributeMap),{value:""}),postCreate:function(){this.setValue(this.value,null);},setValue:function(_1e6,_1e7){this.value=_1e6;this._handleOnChange(_1e6,_1e7);},_getValueDeprecated:false,getValue:function(){return this._lastValue;},undo:function(){this.setValue(this._lastValueReported,false);},_valueChanged:function(){var v=this.getValue();var lv=this._lastValueReported;return ((v!==null&&(v!==undefined)&&v.toString)?v.toString():"")!==((lv!==null&&(lv!==undefined)&&lv.toString)?lv.toString():"");},_onKeyPress:function(e){if(e.keyCode==dojo.keys.ESCAPE&&!e.shiftKey&&!e.ctrlKey&&!e.altKey){if(this._valueChanged()){this.undo();dojo.stopEvent(e);return false;}}return true;}});}if(!dojo._hasResource["dijit.dijit"]){dojo._hasResource["dijit.dijit"]=true;dojo.provide("dijit.dijit");} Copied: branches/vhffs-design/vhffs-panel/js/dijit/dijit.js (from rev 1396, branches/vhffs-design/vhffs-panel/js/dijit/dijit.js) =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/dijit.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dijit/dijit.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,16 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + +/* + This is a compiled version of Dojo, built for deployment and not for + development. To get an editable version, please visit: + + http://dojotoolkit.org + + for documentation and information on getting the source. +*/ + +if(!dojo._hasResource["dijit._base.focus"]){dojo._hasResource["dijit._base.focus"]=true;dojo.provide("dijit._base.focus");dojo.mixin(dijit,{_curFocus:null,_prevFocus:null,isCollapsed:function(){var _1=dojo.doc;if(_1.selection){var s=_1.selection;if(s.type=="Text"){return !s.createRange().htmlText.length;}else{return !s.createRange().length;}}else{var _3=dojo.global;var _4=_3.getSelection();if(dojo.isString(_4)){return !_4;}else{return !_4||_4.isCollapsed||!_4.toString();}}},getBookmark:function(){var _5,_6=dojo.doc.selection;if(_6){var _7=_6.createRange();if(_6.type.toUpperCase()=="CONTROL"){if(_7.length){_5=[];var i=0,_9=_7.length;while(i<_9){_5.push(_7.item(i++));}}else{_5=null;}}else{_5=_7.getBookmark();}}else{if(window.getSelection){_6=dojo.global.getSelection();if(_6){_7=_6.getRangeAt(0);_5=_7.cloneRange();}}else{console.warn("No idea how to store the current selection for this browser!");}}return _5;},moveToBookmark:function(_a){var _b=dojo.doc;if(_b.selection){var _c;if(dojo.isArray(_a)){_c=_b.body.createControlRange();dojo.forEach(_a,function(n){_c.addElement(n);});}else{_c=_b.selection.createRange();_c.moveToBookmark(_a);}_c.select();}else{var _e=dojo.global.getSelection&&dojo.global.getSelection();if(_e&&_e.removeAllRanges){_e.removeAllRanges();_e.addRange(_a);}else{console.warn("No idea how to restore selection for this browser!");}}},getFocus:function(_f,_10){return {node:_f&&dojo.isDescendant(dijit._curFocus,_f.domNode)?dijit._prevFocus:dijit._curFocus,bookmark:!dojo.withGlobal(_10||dojo.global,dijit.isCollapsed)?dojo.withGlobal(_10||dojo.global,dijit.getBookmark):null,openedForWindow:_10};},focus:function(_11){if(!_11){return;}var _12="node" in _11?_11.node:_11,_13=_11.bookmark,_14=_11.openedForWindow;if(_12){var _15=(_12.tagName.toLowerCase()=="iframe")?_12.contentWindow:_12;if(_15&&_15.focus){try{_15.focus();}catch(e){}}dijit._onFocusNode(_12);}if(_13&&dojo.withGlobal(_14||dojo.global,dijit.isCollapsed)){if(_14){_14.focus();}try{dojo.withGlobal(_14||dojo.global,dijit.moveToBookmark,null,[_13]);}catch(e){}}},_activeStack:[],registerIframe:function(_16){dijit.registerWin(_16.contentWindow,_16);},registerWin:function(_17,_18){dojo.connect(_17.document,"onmousedown",function(evt){dijit._justMouseDowned=true;setTimeout(function(){dijit._justMouseDowned=false;},0);dijit._onTouchNode(_18||evt.target||evt.srcElement);});var doc=_17.document;if(doc){if(dojo.isIE){doc.attachEvent("onactivate",function(evt){if(evt.srcElement.tagName.toLowerCase()!="#document"){dijit._onFocusNode(_18||evt.srcElement);}});doc.attachEvent("ondeactivate",function(evt){dijit._onBlurNode(_18||evt.srcElement);});}else{doc.addEventListener("focus",function(evt){dijit._onFocusNode(_18||evt.target);},true);doc.addEventListener("blur",function(evt){dijit._onBlurNode(_18||evt.target);},true);}}doc=null;},_onBlurNode:function(_1f){dijit._prevFocus=dijit._curFocus;dijit._curFocus=null;if(dijit._justMouseDowned){return;}if(dijit._clearActiveWidgetsTimer){clearTimeout(dijit._clearActiveWidgetsTimer);}dijit._clearActiveWidgetsTimer=setTimeout(function(){delete dijit._clearActiveWidgetsTimer;dijit._setStack([]);dijit._prevFocus=null;},100);},_onTouchNode:function(_20){if(dijit._clearActiveWidgetsTimer){clearTimeout(dijit._clearActiveWidgetsTimer);delete dijit._clearActiveWidgetsTimer;}var _21=[];try{while(_20){if(_20.dijitPopupParent){_20=dijit.byId(_20.dijitPopupParent).domNode;}else{if(_20.tagName&&_20.tagName.toLowerCase()=="body"){if(_20===dojo.body()){break;}_20=dijit.getDocumentWindow(_20.ownerDocument).frameElement;}else{var id=_20.getAttribute&&_20.getAttribute("widgetId");if(id){_21.unshift(id);}_20=_20.parentNode;}}}}catch(e){}dijit._setStack(_21);},_onFocusNode:function(_23){if(!_23){return;}if(_23.nodeType==9){return;}dijit._onTouchNode(_23);if(_23==dijit._curFocus){return;}if(dijit._curFocus){dijit._prevFocus=dijit._curFocus;}dijit._curFocus=_23;dojo.publish("focusNode",[_23]);},_setStack:function(_24){var _25=dijit._activeStack;dijit._activeStack=_24;for(var _26=0;_26<Math.min(_25.length,_24.length);_26++){if(_25[_26]!=_24[_26]){break;}}for(var i=_25.length-1;i>=_26;i--){var _28=dijit.byId(_25[i]);if(_28){_28._focused=false;_28._hasBeenBlurred=true;if(_28._onBlur){_28._onBlur();}if(_28._setStateClass){_28._setStateClass();}dojo.publish("widgetBlur",[_28]);}}for(i=_26;i<_24.length;i++){_28=dijit.byId(_24[i]);if(_28){_28._focused=true;if(_28._onFocus){_28._onFocus();}if(_28._setStateClass){_28._setStateClass();}dojo.publish("widgetFocus",[_28]);}}}});dojo.addOnLoad(function(){dijit.registerWin(window);});}if(!dojo._hasResource["dijit._base.manager"]){dojo._hasResource["dijit._base.manager"]=true;dojo.provide("dijit._base.manager");dojo.declare("dijit.WidgetSet",null,{constructor:function(){this._hash={};},add:function(_29){if(this._hash[_29.id]){throw new Error("Tried to register widget with id=="+_29.id+" but that id is already registered");}this._hash[_29.id]=_29;},remove:function(id){delete this._hash[id];},forEach:function(_2b){for(var id in this._hash){_2b(this._hash[id]);}},filter:function(_2d){var res=new dijit.WidgetSet();this.forEach(function(_2f){if(_2d(_2f)){res.add(_2f);}});return res;},byId:function(id){return this._hash[id];},byClass:function(cls){return this.filter(function(_32){return _32.declaredClass==cls;});}});dijit.registry=new dijit.WidgetSet();dijit._widgetTypeCtr={};dijit.getUniqueId=function(_33){var id;do{id=_33+"_"+(_33 in dijit._widgetTypeCtr?++dijit._widgetTypeCtr[_33]:dijit._widgetTypeCtr[_33]=0);}while(dijit.byId(id));return id;};dijit.findWidgets=function(_35){var _36=[];function _37(_38){var _39=dojo.isIE?_38.children:_38.childNodes,i=0,_3b;while(_3b=_39[i++]){if(_3b.nodeType!=1){continue;}var _3c=_3b.getAttribute("widgetId");if(_3c){var _3d=dijit.byId(_3c);_36.push(_3d);}else{_37(_3b);}}};_37(_35);return _36;};if(dojo.isIE){dojo.addOnWindowUnload(function(){dojo.forEach(dijit.findWidgets(dojo.body()),function(_3e){if(_3e.destroyRecursive){_3e.destroyRecursive();}else{if(_3e.destroy){_3e.destroy();}}});});}dijit.byId=function(id){return (dojo.isString(id))?dijit.registry.byId(id):id;};dijit.byNode=function(_40){return dijit.registry.byId(_40.getAttribute("widgetId"));};dijit.getEnclosingWidget=function(_41){while(_41){if(_41.getAttribute&&_41.getAttribute("widgetId")){return dijit.registry.byId(_41.getAttribute("widgetId"));}_41=_41.parentNode;}return null;};dijit._tabElements={area:true,button:true,input:true,object:true,select:true,textarea:true};dijit._isElementShown=function(_42){var _43=dojo.style(_42);return (_43.visibility!="hidden")&&(_43.visibility!="collapsed")&&(_43.display!="none")&&(dojo.attr(_42,"type")!="hidden");};dijit.isTabNavigable=function(_44){if(dojo.hasAttr(_44,"disabled")){return false;}var _45=dojo.hasAttr(_44,"tabindex");var _46=dojo.attr(_44,"tabindex");if(_45&&_46>=0){return true;}var _47=_44.nodeName.toLowerCase();if(((_47=="a"&&dojo.hasAttr(_44,"href"))||dijit._tabElements[_47])&&(!_45||_46>=0)){return true;}return false;};dijit._getTabNavigable=function(_48){var _49,_4a,_4b,_4c,_4d,_4e;var _4f=function(_50){dojo.query("> *",_50).forEach(function(_51){var _52=dijit._isElementShown(_51);if(_52&&dijit.isTabNavigable(_51)){var _53=dojo.attr(_51,"tabindex");if(!dojo.hasAttr(_51,"tabindex")||_53==0){if(!_49){_49=_51;}_4a=_51;}else{if(_53>0){if(!_4b||_53<_4c){_4c=_53;_4b=_51;}if(!_4d||_53>=_4e){_4e=_53;_4d=_51;}}}}if(_52&&_51.nodeName.toUpperCase()!="SELECT"){_4f(_51);}});};if(dijit._isElementShown(_48)){_4f(_48);}return {first:_49,last:_4a,lowest:_4b,highest:_4d};};dijit.getFirstInTabbingOrder=function(_54){var _55=dijit._getTabNavigable(dojo.byId(_54));return _55.lowest?_55.lowest:_55.first;};dijit.getLastInTabbingOrder=function(_56){var _57=dijit._getTabNavigable(dojo.byId(_56));return _57.last?_57.last:_57.highest;};dijit.defaultDuration=dojo.config["defaultDuration"]||200;}if(!dojo._hasResource["dojo.AdapterRegistry"]){dojo._hasResource["dojo.AdapterRegistry"]=true;dojo.provide("dojo.AdapterRegistry");dojo.AdapterRegistry=function(_58){this.pairs=[];this.returnWrappers=_58||false;};dojo.extend(dojo.AdapterRegistry,{register:function(_59,_5a,_5b,_5c,_5d){this.pairs[((_5d)?"unshift":"push")]([_59,_5a,_5b,_5c]);},match:function(){for(var i=0;i<this.pairs.length;i++){var _5f=this.pairs[i];if(_5f[1].apply(this,arguments)){if((_5f[3])||(this.returnWrappers)){return _5f[2];}else{return _5f[2].apply(this,arguments);}}}throw new Error("No match found");},unregister:function(_60){for(var i=0;i<this.pairs.length;i++){var _62=this.pairs[i];if(_62[0]==_60){this.pairs.splice(i,1);return true;}}return false;}});}if(!dojo._hasResource["dijit._base.place"]){dojo._hasResource["dijit._base.place"]=true;dojo.provide("dijit._base.place");dijit.getViewport=function(){var _63=(dojo.doc.compatMode=="BackCompat")?dojo.body():dojo.doc.documentElement;var _64=dojo._docScroll();return {w:_63.clientWidth,h:_63.clientHeight,l:_64.x,t:_64.y};};dijit.placeOnScreen=function(_65,pos,_67,_68){var _69=dojo.map(_67,function(_6a){var c={corner:_6a,pos:{x:pos.x,y:pos.y}};if(_68){c.pos.x+=_6a.charAt(1)=="L"?_68.x:-_68.x;c.pos.y+=_6a.charAt(0)=="T"?_68.y:-_68.y;}return c;});return dijit._place(_65,_69);};dijit._place=function(_6c,_6d,_6e){var _6f=dijit.getViewport();if(!_6c.parentNode||String(_6c.parentNode.tagName).toLowerCase()!="body"){dojo.body().appendChild(_6c);}var _70=null;dojo.some(_6d,function(_71){var _72=_71.corner;var pos=_71.pos;if(_6e){_6e(_6c,_71.aroundCorner,_72);}var _74=_6c.style;var _75=_74.display;var _76=_74.visibility;_74.visibility="hidden";_74.display="";var mb=dojo.marginBox(_6c);_74.display=_75;_74.visibility=_76;var _78=(_72.charAt(1)=="L"?pos.x:Math.max(_6f.l,pos.x-mb.w)),_79=(_72.charAt(0)=="T"?pos.y:Math.max(_6f.t,pos.y-mb.h)),_7a=(_72.charAt(1)=="L"?Math.min(_6f.l+_6f.w,_78+mb.w):pos.x),_7b=(_72.charAt(0)=="T"?Math.min(_6f.t+_6f.h,_79+mb.h):pos.y),_7c=_7a-_78,_7d=_7b-_79,_7e=(mb.w-_7c)+(mb.h-_7d);if(_70==null||_7e<_70.overflow){_70={corner:_72,aroundCorner:_71.aroundCorner,x:_78,y:_79,w:_7c,h:_7d,overflow:_7e};}return !_7e;});_6c.style.left=_70.x+"px";_6c.style.top=_70.y+"px";if(_70.overflow&&_6e){_6e(_6c,_70.aroundCorner,_70.corner);}return _70;};dijit.placeOnScreenAroundNode=function(_7f,_80,_81,_82){_80=dojo.byId(_80);var _83=_80.style.display;_80.style.display="";var _84=_80.offsetWidth;var _85=_80.offsetHeight;var _86=dojo.coords(_80,true);_80.style.display=_83;return dijit._placeOnScreenAroundRect(_7f,_86.x,_86.y,_84,_85,_81,_82);};dijit.placeOnScreenAroundRectangle=function(_87,_88,_89,_8a){return dijit._placeOnScreenAroundRect(_87,_88.x,_88.y,_88.width,_88.height,_89,_8a);};dijit._placeOnScreenAroundRect=function(_8b,x,y,_8e,_8f,_90,_91){var _92=[];for(var _93 in _90){_92.push({aroundCorner:_93,corner:_90[_93],pos:{x:x+(_93.charAt(1)=="L"?0:_8e),y:y+(_93.charAt(0)=="T"?0:_8f)}});}return dijit._place(_8b,_92,_91);};dijit.placementRegistry=new dojo.AdapterRegistry();dijit.placementRegistry.register("node",function(n,x){return typeof x=="object"&&typeof x.offsetWidth!="undefined"&&typeof x.offsetHeight!="undefined";},dijit.placeOnScreenAroundNode);dijit.placementRegistry.register("rect",function(n,x){return typeof x=="object"&&"x" in x&&"y" in x&&"width" in x&&"height" in x;},dijit.placeOnScreenAroundRectangle);dijit.placeOnScreenAroundElement=function(_98,_99,_9a,_9b){return dijit.placementRegistry.match.apply(dijit.placementRegistry,arguments);};}if(!dojo._hasResource["dijit._base.window"]){dojo._hasResource["dijit._base.window"]=true;dojo.provide("dijit._base.window");dijit.getDocumentWindow=function(doc){if(dojo.isIE&&window!==document.parentWindow&&!doc._parentWindow){doc.parentWindow.execScript("document._parentWindow = window;","Javascript");var win=doc._parentWindow;doc._parentWindow=null;return win;}return doc._parentWindow||doc.parentWindow||doc.defaultView;};}if(!dojo._hasResource["dijit._base.popup"]){dojo._hasResource["dijit._base.popup"]=true;dojo.provide("dijit._base.popup");dijit.popup=new function(){var _9e=[],_9f=1000,_a0=1;this.prepare=function(_a1){var s=_a1.style;s.visibility="hidden";s.position="absolute";s.top="-9999px";if(s.display=="none"){s.display="";}dojo.body().appendChild(_a1);};this.open=function(_a3){var _a4=_a3.popup,_a5=_a3.orient||{"BL":"TL","TL":"BL"},_a6=_a3.around,id=(_a3.around&&_a3.around.id)?(_a3.around.id+"_dropdown"):("popup_"+_a0++);var _a8=dojo.create("div",{id:id,"class":"dijitPopup",style:{zIndex:_9f+_9e.length,visibility:"hidden"}},dojo.body());dijit.setWaiRole(_a8,"presentation");_a8.style.left=_a8.style.top="0px";if(_a3.parent){_a8.dijitPopupParent=_a3.parent.id;}var s=_a4.domNode.style;s.display="";s.visibility="";s.position="";s.top="0px";_a8.appendChild(_a4.domNode);var _aa=new dijit.BackgroundIframe(_a8);var _ab=_a6?dijit.placeOnScreenAroundElement(_a8,_a6,_a5,_a4.orient?dojo.hitch(_a4,"orient"):null):dijit.placeOnScreen(_a8,_a3,_a5=="R"?["TR","BR","TL","BL"]:["TL","BL","TR","BR"],_a3.padding);_a8.style.visibility="visible";var _ac=[];var _ad=function(){for(var pi=_9e.length-1;pi>0&&_9e[pi].parent===_9e[pi-1].widget;pi--){}return _9e[pi];};_ac.push(dojo.connect(_a8,"onkeypress",this,function(evt){if(evt.charOrCode==dojo.keys.ESCAPE&&_a3.onCancel){dojo.stopEvent(evt);_a3.onCancel();}else{if(evt.charOrCode===dojo.keys.TAB){dojo.stopEvent(evt);var _b0=_ad();if(_b0&&_b0.onCancel){_b0.onCancel();}}}}));if(_a4.onCancel){_ac.push(dojo.connect(_a4,"onCancel",null,_a3.onCancel));}_ac.push(dojo.connect(_a4,_a4.onExecute?"onExecute":"onChange",null,function(){var _b1=_ad();if(_b1&&_b1.onExecute){_b1.onExecute();}}));_9e.push({wrapper:_a8,iframe:_aa,widget:_a4,parent:_a3.parent,onExecute:_a3.onExecute,onCancel:_a3.onCancel,onClose:_a3.onClose,handlers:_ac});if(_a4.onOpen){_a4.onOpen(_ab);}return _ab;};this.close=function(_b2){while(dojo.some(_9e,function(_b3){return _b3.widget==_b2;})){var top=_9e.pop(),_b5=top.wrapper,_b6=top.iframe,_b7=top.widget,_b8=top.onClose;if(_b7.onClose){_b7.onClose();}dojo.forEach(top.handlers,dojo.disconnect);if(!_b7||!_b7.domNode){return;}this.prepare(_b7.domNode);_b6.destroy();dojo.destroy(_b5);if(_b8){_b8();}}};}();dijit._frames=new function(){var _b9=[];this.pop=function(){var _ba;if(_b9.length){_ba=_b9.pop();_ba.style.display="";}else{if(dojo.isIE){var _bb=dojo.config["dojoBlankHtmlUrl"]||(dojo.moduleUrl("dojo","resources/blank.html")+"")||"javascript:\"\"";var _bc="<iframe src='"+_bb+"'"+" style='position: absolute; left: 0px; top: 0px;"+"z-index: -1; filter:Alpha(Opacity=\"0\");'>";_ba=dojo.doc.createElement(_bc);}else{_ba=dojo.create("iframe");_ba.src="javascript:\"\"";_ba.className="dijitBackgroundIframe";}_ba.tabIndex=-1;dojo.body().appendChild(_ba);}return _ba;};this.push=function(_bd){_bd.style.display="none";if(dojo.isIE){_bd.style.removeExpression("width");_bd.style.removeExpression("height");}_b9.push(_bd);};}();dijit.BackgroundIframe=function(_be){if(!_be.id){throw new Error("no id");}if(dojo.isIE<7||(dojo.isFF<3&&dojo.hasClass(dojo.body(),"dijit_a11y"))){var _bf=dijit._frames.pop();_be.appendChild(_bf);if(dojo.isIE){_bf.style.setExpression("width",dojo._scopeName+".doc.getElementById('"+_be.id+"').offsetWidth");_bf.style.setExpression("height",dojo._scopeName+".doc.getElementById('"+_be.id+"').offsetHeight");}this.iframe=_bf;}};dojo.extend(dijit.BackgroundIframe,{destroy:function(){if(this.iframe){dijit._frames.push(this.iframe);delete this.iframe;}}});}if(!dojo._hasResource["dijit._base.scroll"]){dojo._hasResource["dijit._base.scroll"]=true;dojo.provide("dijit._base.scroll");dijit.scrollIntoView=function(_c0){try{_c0=dojo.byId(_c0);var doc=dojo.doc;var _c2=dojo.body();var _c3=_c2.parentNode;if((!(dojo.isFF>=3||dojo.isIE||dojo.isWebKit)||_c0==_c2||_c0==_c3)&&(typeof _c0.scrollIntoView=="function")){_c0.scrollIntoView(false);return;}var ltr=dojo._isBodyLtr();var _c5=dojo.isIE>=8&&!_c6;var rtl=!ltr&&!_c5;var _c8=_c2;var _c6=doc.compatMode=="BackCompat";if(_c6){_c3._offsetWidth=_c3._clientWidth=_c2._offsetWidth=_c2.clientWidth;_c3._offsetHeight=_c3._clientHeight=_c2._offsetHeight=_c2.clientHeight;}else{if(dojo.isWebKit){_c2._offsetWidth=_c2._clientWidth=_c3.clientWidth;_c2._offsetHeight=_c2._clientHeight=_c3.clientHeight;}else{_c8=_c3;}_c3._offsetHeight=_c3.clientHeight;_c3._offsetWidth=_c3.clientWidth;}function _c9(_ca){var ie=dojo.isIE;return ((ie<=6||(ie>=7&&_c6))?false:(dojo.style(_ca,"position").toLowerCase()=="fixed"));};function _cc(_cd){var _ce=_cd.parentNode;var _cf=_cd.offsetParent;if(_cf==null||_c9(_cd)){_cf=_c3;_ce=(_cd==_c2)?_c3:null;}_cd._offsetParent=_cf;_cd._parent=_ce;var bp=dojo._getBorderExtents(_cd);_cd._borderStart={H:(_c5&&!ltr)?(bp.w-bp.l):bp.l,V:bp.t};_cd._borderSize={H:bp.w,V:bp.h};_cd._scrolledAmount={H:_cd.scrollLeft,V:_cd.scrollTop};_cd._offsetSize={H:_cd._offsetWidth||_cd.offsetWidth,V:_cd._offsetHeight||_cd.offsetHeight};_cd._offsetStart={H:(_c5&&!ltr)?_cf.clientWidth-_cd.offsetLeft-_cd._offsetSize.H:_cd.offsetLeft,V:_cd.offsetTop};_cd._clientSize={H:_cd._clientWidth||_cd.clientWidth,V:_cd._clientHeight||_cd.clientHeight};if(_cd!=_c2&&_cd!=_c3&&_cd!=_c0){for(var dir in _cd._offsetSize){var _d2=_cd._offsetSize[dir]-_cd._clientSize[dir]-_cd._borderSize[dir];var _d3=_cd._clientSize[dir]>0&&_d2>0;if(_d3){_cd._offsetSize[dir]-=_d2;if(dojo.isIE&&rtl&&dir=="H"){_cd._offsetStart[dir]+=_d2;}}}}};var _d4=_c0;while(_d4!=null){if(_c9(_d4)){_c0.scrollIntoView(false);return;}_cc(_d4);_d4=_d4._parent;}if(dojo.isIE&&_c0._parent){var _d5=_c0._offsetParent;_c0._offsetStart.H+=_d5._borderStart.H;_c0._offsetStart.V+=_d5._borderStart.V;}if(dojo.isIE>=7&&_c8==_c3&&rtl&&_c2._offsetStart&&_c2._offsetStart.H==0){var _d6=_c3.scrollWidth-_c3._offsetSize.H;if(_d6>0){_c2._offsetStart.H=-_d6;}}if(dojo.isIE<=6&&!_c6){_c3._offsetSize.H+=_c3._borderSize.H;_c3._offsetSize.V+=_c3._borderSize.V;}if(rtl&&_c2._offsetStart&&_c8==_c3&&_c3._scrolledAmount){var ofs=_c2._offsetStart.H;if(ofs<0){_c3._scrolledAmount.H+=ofs;_c2._offsetStart.H=0;}}_d4=_c0;while(_d4){var _d8=_d4._parent;if(!_d8){break;}if(_d8.tagName=="TD"){var _d9=_d8._parent._parent._parent;if(_d8!=_d4._offsetParent&&_d8._offsetParent!=_d4._offsetParent){_d8=_d9;}}var _da=_d4._offsetParent==_d8;for(var dir in _d4._offsetStart){var _dc=dir=="H"?"V":"H";if(rtl&&dir=="H"&&(_d8!=_c3)&&(_d8!=_c2)&&(dojo.isIE||dojo.isWebKit)&&_d8._clientSize.H>0&&_d8.scrollWidth>_d8._clientSize.H){var _dd=_d8.scrollWidth-_d8._clientSize.H;if(_dd>0){_d8._scrolledAmount.H-=_dd;}}if(_d8._offsetParent.tagName=="TABLE"){if(dojo.isIE){_d8._offsetStart[dir]-=_d8._offsetParent._borderStart[dir];_d8._borderStart[dir]=_d8._borderSize[dir]=0;}else{_d8._offsetStart[dir]+=_d8._offsetParent._borderStart[dir];}}if(dojo.isIE){_d8._offsetStart[dir]+=_d8._offsetParent._borderStart[dir];}var _de=_d4._offsetStart[dir]-_d8._scrolledAmount[dir]-(_da?0:_d8._offsetStart[dir])-_d8._borderStart[dir];var _df=_de+_d4._offsetSize[dir]-_d8._offsetSize[dir]+_d8._borderSize[dir];var _e0=(dir=="H")?"scrollLeft":"scrollTop";var _e1=dir=="H"&&rtl;var _e2=_e1?-_df:_de;var _e3=_e1?-_de:_df;var _e4=(_e2*_e3<=0)?0:Math[(_e2<0)?"max":"min"](_e2,_e3);if(_e4!=0){var _e5=_d8[_e0];_d8[_e0]+=(_e1)?-_e4:_e4;var _e6=_d8[_e0]-_e5;}if(_da){_d4._offsetStart[dir]+=_d8._offsetStart[dir];}_d4._offsetStart[dir]-=_d8[_e0];}_d4._parent=_d8._parent;_d4._offsetParent=_d8._offsetParent;}_d8=_c0;var _e7;while(_d8&&_d8.removeAttribute){_e7=_d8.parentNode;_d8.removeAttribute("_offsetParent");_d8.removeAttribute("_parent");_d8=_e7;}}catch(error){console.error("scrollIntoView: "+error);_c0.scrollIntoView(false);}};}if(!dojo._hasResource["dijit._base.sniff"]){dojo._hasResource["dijit._base.sniff"]=true;dojo.provide("dijit._base.sniff");(function(){var d=dojo,_e9=d.doc.documentElement,ie=d.isIE,_eb=d.isOpera,maj=Math.floor,ff=d.isFF,_ee=d.boxModel.replace(/-/,""),_ef={dj_ie:ie,dj_ie6:maj(ie)==6,dj_ie7:maj(ie)==7,dj_iequirks:ie&&d.isQuirks,dj_opera:_eb,dj_opera8:maj(_eb)==8,dj_opera9:maj(_eb)==9,dj_khtml:d.isKhtml,dj_webkit:d.isWebKit,dj_safari:d.isSafari,dj_gecko:d.isMozilla,dj_ff2:maj(ff)==2,dj_ff3:maj(ff)==3};_ef["dj_"+_ee]=true;for(var p in _ef){if(_ef[p]){if(_e9.className){_e9.className+=" "+p;}else{_e9.className=p;}}}dojo._loaders.unshift(function(){if(!dojo._isBodyLtr()){_e9.className+=" dijitRtl";for(var p in _ef){if(_ef[p]){_e9.className+=" "+p+"-rtl";}}}});})();}if(!dojo._hasResource["dijit._base.typematic"]){dojo._hasResource["dijit._base.typematic"]=true;dojo.provide("dijit._base.typematic");dijit.typematic={_fireEventAndReload:function(){this._timer=null;this._callback(++this._count,this._node,this._evt);this._currentTimeout=(this._currentTimeout<0)?this._initialDelay:((this._subsequentDelay>1)?this._subsequentDelay:Math.round(this._currentTimeout*this._subsequentDelay));this._timer=setTimeout(dojo.hitch(this,"_fireEventAndReload"),this._currentTimeout);},trigger:function(evt,_f3,_f4,_f5,obj,_f7,_f8){if(obj!=this._obj){this.stop();this._initialDelay=_f8||500;this._subsequentDelay=_f7||0.9;this._obj=obj;this._evt=evt;this._node=_f4;this._currentTimeout=-1;this._count=-1;this._callback=dojo.hitch(_f3,_f5);this._fireEventAndReload();}},stop:function(){if(this._timer){clearTimeout(this._timer);this._timer=null;}if(this._obj){this._callback(-1,this._node,this._evt);this._obj=null;}},addKeyListener:function(_f9,_fa,_fb,_fc,_fd,_fe){if(_fa.keyCode){_fa.charOrCode=_fa.keyCode;dojo.deprecated("keyCode attribute parameter for dijit.typematic.addKeyListener is deprecated. Use charOrCode instead.","","2.0");}else{if(_fa.charCode){_fa.charOrCode=String.fromCharCode(_fa.charCode);dojo.deprecated("charCode attribute parameter for dijit.typematic.addKeyListener is deprecated. Use charOrCode instead.","","2.0");}}return [dojo.connect(_f9,"onkeypress",this,function(evt){if(evt.charOrCode==_fa.charOrCode&&(_fa.ctrlKey===undefined||_fa.ctrlKey==evt.ctrlKey)&&(_fa.altKey===undefined||_fa.altKey==evt.ctrlKey)&&(_fa.shiftKey===undefined||_fa.shiftKey==evt.ctrlKey)){dojo.stopEvent(evt);dijit.typematic.trigger(_fa,_fb,_f9,_fc,_fa,_fd,_fe);}else{if(dijit.typematic._obj==_fa){dijit.typematic.stop();}}}),dojo.connect(_f9,"onkeyup",this,function(evt){if(dijit.typematic._obj==_fa){dijit.typematic.stop();}})];},addMouseListener:function(node,_102,_103,_104,_105){var dc=dojo.connect;return [dc(node,"mousedown",this,function(evt){dojo.stopEvent(evt);dijit.typematic.trigger(evt,_102,node,_103,node,_104,_105);}),dc(node,"mouseup",this,function(evt){dojo.stopEvent(evt);dijit.typematic.stop();}),dc(node,"mouseout",this,function(evt){dojo.stopEvent(evt);dijit.typematic.stop();}),dc(node,"mousemove",this,function(evt){dojo.stopEvent(evt);}),dc(node,"dblclick",this,function(evt){dojo.stopEvent(evt);if(dojo.isIE){dijit.typematic.trigger(evt,_102,node,_103,node,_104,_105);setTimeout(dojo.hitch(this,dijit.typematic.stop),50);}})];},addListener:function(_10c,_10d,_10e,_10f,_110,_111,_112){return this.addKeyListener(_10d,_10e,_10f,_110,_111,_112).concat(this.addMouseListener(_10c,_10f,_110,_111,_112));}};}if(!dojo._hasResource["dijit._base.wai"]){dojo._hasResource["dijit._base.wai"]=true;dojo.provide("dijit._base.wai");dijit.wai={onload:function(){var div=dojo.create("div",{id:"a11yTestNode",style:{cssText:"border: 1px solid;"+"border-color:red green;"+"position: absolute;"+"height: 5px;"+"top: -999px;"+"background-image: url(\""+(dojo.config.blankGif||dojo.moduleUrl("dojo","resources/blank.gif"))+"\");"}},dojo.body());var cs=dojo.getComputedStyle(div);if(cs){var _115=cs.backgroundImage;var _116=(cs.borderTopColor==cs.borderRightColor)||(_115!=null&&(_115=="none"||_115=="url(invalid-url:)"));dojo[_116?"addClass":"removeClass"](dojo.body(),"dijit_a11y");if(dojo.isIE){div.outerHTML="";}else{dojo.body().removeChild(div);}}}};if(dojo.isIE||dojo.isMoz){dojo._loaders.unshift(dijit.wai.onload);}dojo.mixin(dijit,{_XhtmlRoles:/banner|contentinfo|definition|main|navigation|search|note|secondary|seealso/,hasWaiRole:function(elem,role){var _119=this.getWaiRole(elem);return role?(_119.indexOf(role)>-1):(_119.length>0);},getWaiRole:function(elem){return dojo.trim((dojo.attr(elem,"role")||"").replace(this._XhtmlRoles,"").replace("wairole:",""));},setWaiRole:function(elem,role){var _11d=dojo.attr(elem,"role")||"";if(dojo.isFF<3||!this._XhtmlRoles.test(_11d)){dojo.attr(elem,"role",dojo.isFF<3?"wairole:"+role:role);}else{if((" "+_11d+" ").indexOf(" "+role+" ")<0){var _11e=dojo.trim(_11d.replace(this._XhtmlRoles,""));var _11f=dojo.trim(_11d.replace(_11e,""));dojo.attr(elem,"role",_11f+(_11f?" ":"")+role);}}},removeWaiRole:function(elem,role){var _122=dojo.attr(elem,"role");if(!_122){return;}if(role){var _123=dojo.isFF<3?"wairole:"+role:role;var t=dojo.trim((" "+_122+" ").replace(" "+_123+" "," "));dojo.attr(elem,"role",t);}else{elem.removeAttribute("role");}},hasWaiState:function(elem,_126){if(dojo.isFF<3){return elem.hasAttributeNS("http://www.w3.org/2005/07/aaa",_126);}return elem.hasAttribute?elem.hasAttribute("aria-"+_126):!!elem.getAttribute("aria-"+_126);},getWaiState:function(elem,_128){if(dojo.isFF<3){return elem.getAttributeNS("http://www.w3.org/2005/07/aaa",_128);}return elem.getAttribute("aria-"+_128)||"";},setWaiState:function(elem,_12a,_12b){if(dojo.isFF<3){elem.setAttributeNS("http://www.w3.org/2005/07/aaa","aaa:"+_12a,_12b);}else{elem.setAttribute("aria-"+_12a,_12b);}},removeWaiState:function(elem,_12d){if(dojo.isFF<3){elem.removeAttributeNS("http://www.w3.org/2005/07/aaa",_12d);}else{elem.removeAttribute("aria-"+_12d);}}});}if(!dojo._hasResource["dijit._base"]){dojo._hasResource["dijit._base"]=true;dojo.provide("dijit._base");}if(!dojo._hasResource["dojo.date.stamp"]){dojo._hasResource["dojo.date.stamp"]=true;dojo.provide("dojo.date.stamp");dojo.date.stamp.fromISOString=function(_12e,_12f){if(!dojo.date.stamp._isoRegExp){dojo.date.stamp._isoRegExp=/^(?:(\d{4})(?:-(\d{2})(?:-(\d{2}))?)?)?(?:T(\d{2}):(\d{2})(?::(\d{2})(.\d+)?)?((?:[+-](\d{2}):(\d{2}))|Z)?)?$/;}var _130=dojo.date.stamp._isoRegExp.exec(_12e);var _131=null;if(_130){_130.shift();if(_130[1]){_130[1]--;}if(_130[6]){_130[6]*=1000;}if(_12f){_12f=new Date(_12f);dojo.map(["FullYear","Month","Date","Hours","Minutes","Seconds","Milliseconds"],function(prop){return _12f["get"+prop]();}).forEach(function(_133,_134){if(_130[_134]===undefined){_130[_134]=_133;}});}_131=new Date(_130[0]||1970,_130[1]||0,_130[2]||1,_130[3]||0,_130[4]||0,_130[5]||0,_130[6]||0);var _135=0;var _136=_130[7]&&_130[7].charAt(0);if(_136!="Z"){_135=((_130[8]||0)*60)+(Number(_130[9])||0);if(_136!="-"){_135*=-1;}}if(_136){_135-=_131.getTimezoneOffset();}if(_135){_131.setTime(_131.getTime()+_135*60000);}}return _131;};dojo.date.stamp.toISOString=function(_137,_138){var _=function(n){return (n<10)?"0"+n:n;};_138=_138||{};var _13b=[];var _13c=_138.zulu?"getUTC":"get";var date="";if(_138.selector!="time"){var year=_137[_13c+"FullYear"]();date=["0000".substr((year+"").length)+year,_(_137[_13c+"Month"]()+1),_(_137[_13c+"Date"]())].join("-");}_13b.push(date);if(_138.selector!="date"){var time=[_(_137[_13c+"Hours"]()),_(_137[_13c+"Minutes"]()),_(_137[_13c+"Seconds"]())].join(":");var _140=_137[_13c+"Milliseconds"]();if(_138.milliseconds){time+="."+(_140<100?"0":"")+_(_140);}if(_138.zulu){time+="Z";}else{if(_138.selector!="time"){var _141=_137.getTimezoneOffset();var _142=Math.abs(_141);time+=(_141>0?"-":"+")+_(Math.floor(_142/60))+":"+_(_142%60);}}_13b.push(time);}return _13b.join("T");};}if(!dojo._hasResource["dojo.parser"]){dojo._hasResource["dojo.parser"]=true;dojo.provide("dojo.parser");dojo.parser=new function(){var d=dojo;var _144=d._scopeName+"Type";var qry="["+_144+"]";var _146=0,_147={};var _148=function(_149,_14a){var nso=_14a||_147;if(dojo.isIE){var cn=_149["__dojoNameCache"];if(cn&&nso[cn]===_149){return cn;}}var name;do{name="__"+_146++;}while(name in nso);nso[name]=_149;return name;};function _14e(_14f){if(d.isString(_14f)){return "string";}if(typeof _14f=="number"){return "number";}if(typeof _14f=="boolean"){return "boolean";}if(d.isFunction(_14f)){return "function";}if(d.isArray(_14f)){return "array";}if(_14f instanceof Date){return "date";}if(_14f instanceof d._Url){return "url";}return "object";};function _150(_151,type){switch(type){case "string":return _151;case "number":return _151.length?Number(_151):NaN;case "boolean":return typeof _151=="boolean"?_151:!(_151.toLowerCase()=="false");case "function":if(d.isFunction(_151)){_151=_151.toString();_151=d.trim(_151.substring(_151.indexOf("{")+1,_151.length-1));}try{if(_151.search(/[^\w\.]+/i)!=-1){_151=_148(new Function(_151),this);}return d.getObject(_151,false);}catch(e){return new Function();}case "array":return _151?_151.split(/\s*,\s*/):[];case "date":switch(_151){case "":return new Date("");case "now":return new Date();default:return d.date.stamp.fromISOString(_151);}case "url":return d.baseUrl+_151;default:return d.fromJson(_151);}};var _153={};function _154(_155){if(!_153[_155]){var cls=d.getObject(_155);if(!d.isFunction(cls)){throw new Error("Could not load class '"+_155+"'. Did you spell the name correctly and use a full path, like 'dijit.form.Button'?");}var _157=cls.prototype;var _158={},_159={};for(var name in _157){if(name.charAt(0)=="_"){continue;}if(name in _159){continue;}var _15b=_157[name];_158[name]=_14e(_15b);}_153[_155]={cls:cls,params:_158};}return _153[_155];};this._functionFromScript=function(_15c){var _15d="";var _15e="";var _15f=_15c.getAttribute("args");if(_15f){d.forEach(_15f.split(/\s*,\s*/),function(part,idx){_15d+="var "+part+" = arguments["+idx+"]; ";});}var _162=_15c.getAttribute("with");if(_162&&_162.length){d.forEach(_162.split(/\s*,\s*/),function(part){_15d+="with("+part+"){";_15e+="}";});}return new Function(_15d+_15c.innerHTML+_15e);};this.instantiate=function(_164,_165){var _166=[];_165=_165||{};d.forEach(_164,function(node){if(!node){return;}var type=_144 in _165?_165[_144]:node.getAttribute(_144);if(!type||!type.length){return;}var _169=_154(type),_16a=_169.cls,ps=_16a._noScript||_16a.prototype._noScript;var _16c={},_16d=node.attributes;for(var name in _169.params){var item=name in _165?{value:_165[name],specified:true}:_16d.getNamedItem(name);if(!item||(!item.specified&&(!dojo.isIE||name.toLowerCase()!="value"))){continue;}var _170=item.value;switch(name){case "class":_170="className" in _165?_165.className:node.className;break;case "style":_170="style" in _165?_165.style:(node.style&&node.style.cssText);}var _171=_169.params[name];if(typeof _170=="string"){_16c[name]=_150(_170,_171);}else{_16c[name]=_170;}}if(!ps){var _172=[],_173=[];d.query("> script[type^='dojo/']",node).orphan().forEach(function(_174){var _175=_174.getAttribute("event"),type=_174.getAttribute("type"),nf=d.parser._functionFromScript(_174);if(_175){if(type=="dojo/connect"){_172.push({event:_175,func:nf});}else{_16c[_175]=nf;}}else{_173.push(nf);}});}var _177=_16a["markupFactory"];if(!_177&&_16a["prototype"]){_177=_16a.prototype["markupFactory"];}var _178=_177?_177(_16c,node,_16a):new _16a(_16c,node);_166.push(_178);var _179=node.getAttribute("jsId");if(_179){d.setObject(_179,_178);}if(!ps){d.forEach(_172,function(_17a){d.connect(_178,_17a.event,null,_17a.func);});d.forEach(_173,function(func){func.call(_178);});}});d.forEach(_166,function(_17c){if(_17c&&_17c.startup&&!_17c._started&&(!_17c.getParent||!_17c.getParent())){_17c.startup();}});return _166;};this.parse=function(_17d){var list=d.query(qry,_17d);var _17f=this.instantiate(list);return _17f;};}();(function(){var _180=function(){if(dojo.config["parseOnLoad"]==true){dojo.parser.parse();}};if(dojo.exists("dijit.wai.onload")&&(dijit.wai.onload===dojo._loaders[0])){dojo._loaders.splice(1,0,_180);}else{dojo._loaders.unshift(_180);}})();}if(!dojo._hasResource["dijit._Widget"]){dojo._hasResource["dijit._Widget"]=true;dojo.provide("dijit._Widget");dojo.require("dijit._base");dojo.connect(dojo,"connect",function(_181,_182){if(_181&&dojo.isFunction(_181._onConnect)){_181._onConnect(_182);}});dijit._connectOnUseEventHandler=function(_183){};(function(){var _184={};var _185=function(dc){if(!_184[dc]){var r=[];var _188;var _189=dojo.getObject(dc).prototype;for(var _18a in _189){if(dojo.isFunction(_189[_18a])&&(_188=_18a.match(/^_set([a-zA-Z]*)Attr$/))&&_188[1]){r.push(_188[1].charAt(0).toLowerCase()+_188[1].substr(1));}}_184[dc]=r;}return _184[dc]||[];};dojo.declare("dijit._Widget",null,{id:"",lang:"",dir:"","class":"",style:"",title:"",srcNodeRef:null,domNode:null,containerNode:null,attributeMap:{id:"",dir:"",lang:"","class":"",style:"",title:""},_deferredConnects:{onClick:"",onDblClick:"",onKeyDown:"",onKeyPress:"",onKeyUp:"",onMouseMove:"",onMouseDown:"",onMouseOut:"",onMouseOver:"",onMouseLeave:"",onMouseEnter:"",onMouseUp:""},onClick:dijit._connectOnUseEventHandler,onDblClick:dijit._connectOnUseEventHandler,onKeyDown:dijit._connectOnUseEventHandler,onKeyPress:dijit._connectOnUseEventHandler,onKeyUp:dijit._connectOnUseEventHandler,onMouseDown:dijit._connectOnUseEventHandler,onMouseMove:dijit._connectOnUseEventHandler,onMouseOut:dijit._connectOnUseEventHandler,onMouseOver:dijit._connectOnUseEventHandler,onMouseLeave:dijit._connectOnUseEventHandler,onMouseEnter:dijit._connectOnUseEventHandler,onMouseUp:dijit._connectOnUseEventHandler,_blankGif:(dojo.config.blankGif||dojo.moduleUrl("dojo","resources/blank.gif")),postscript:function(_18b,_18c){this.create(_18b,_18c);},create:function(_18d,_18e){this.srcNodeRef=dojo.byId(_18e);this._connects=[];this._deferredConnects=dojo.clone(this._deferredConnects);for(var attr in this.attributeMap){delete this._deferredConnects[attr];}for(attr in this._deferredConnects){if(this[attr]!==dijit._connectOnUseEventHandler){delete this._deferredConnects[attr];}}if(this.srcNodeRef&&(typeof this.srcNodeRef.id=="string")){this.id=this.srcNodeRef.id;}if(_18d){this.params=_18d;dojo.mixin(this,_18d);}this.postMixInProperties();if(!this.id){this.id=dijit.getUniqueId(this.declaredClass.replace(/\./g,"_"));}dijit.registry.add(this);this.buildRendering();if(this.domNode){this._applyAttributes();var _190=this.srcNodeRef;if(_190&&_190.parentNode){_190.parentNode.replaceChild(this.domNode,_190);}for(attr in this.params){this._onConnect(attr);}}if(this.domNode){this.domNode.setAttribute("widgetId",this.id);}this.postCreate();if(this.srcNodeRef&&!this.srcNodeRef.parentNode){delete this.srcNodeRef;}this._created=true;},_applyAttributes:function(){var _191=function(attr,_193){if((_193.params&&attr in _193.params)||_193[attr]){_193.attr(attr,_193[attr]);}};for(var attr in this.attributeMap){_191(attr,this);}dojo.forEach(_185(this.declaredClass),function(a){if(!(a in this.attributeMap)){_191(a,this);}},this);},postMixInProperties:function(){},buildRendering:function(){this.domNode=this.srcNodeRef||dojo.create("div");},postCreate:function(){},startup:function(){this._started=true;},destroyRecursive:function(_196){this.destroyDescendants(_196);this.destroy(_196);},destroy:function(_197){this.uninitialize();dojo.forEach(this._connects,function(_198){dojo.forEach(_198,dojo.disconnect);});dojo.forEach(this._supportingWidgets||[],function(w){if(w.destroy){w.destroy();}});this.destroyRendering(_197);dijit.registry.remove(this.id);},destroyRendering:function(_19a){if(this.bgIframe){this.bgIframe.destroy(_19a);delete this.bgIframe;}if(this.domNode){if(_19a){dojo.removeAttr(this.domNode,"widgetId");}else{dojo.destroy(this.domNode);}delete this.domNode;}if(this.srcNodeRef){if(!_19a){dojo.destroy(this.srcNodeRef);}delete this.srcNodeRef;}},destroyDescendants:function(_19b){dojo.forEach(this.getChildren(),function(_19c){if(_19c.destroyRecursive){_19c.destroyRecursive(_19b);}});},uninitialize:function(){return false;},onFocus:function(){},onBlur:function(){},_onFocus:function(e){this.onFocus();},_onBlur:function(){this.onBlur();},_onConnect:function(_19e){if(_19e in this._deferredConnects){var _19f=this[this._deferredConnects[_19e]||"domNode"];this.connect(_19f,_19e.toLowerCase(),_19e);delete this._deferredConnects[_19e];}},_setClassAttr:function(_1a0){var _1a1=this[this.attributeMap["class"]||"domNode"];dojo.removeClass(_1a1,this["class"]);this["class"]=_1a0;dojo.addClass(_1a1,_1a0);},_setStyleAttr:function(_1a2){var _1a3=this[this.attributeMap["style"]||"domNode"];if(dojo.isObject(_1a2)){dojo.style(_1a3,_1a2);}else{if(_1a3.style.cssText){_1a3.style.cssText+="; "+_1a2;}else{_1a3.style.cssText=_1a2;}}this["style"]=_1a2;},setAttribute:function(attr,_1a5){dojo.deprecated(this.declaredClass+"::setAttribute() is deprecated. Use attr() instead.","","2.0");this.attr(attr,_1a5);},_attrToDom:function(attr,_1a7){var _1a8=this.attributeMap[attr];dojo.forEach(dojo.isArray(_1a8)?_1a8:[_1a8],function(_1a9){var _1aa=this[_1a9.node||_1a9||"domNode"];var type=_1a9.type||"attribute";switch(type){case "attribute":if(dojo.isFunction(_1a7)){_1a7=dojo.hitch(this,_1a7);}if(/^on[A-Z][a-zA-Z]*$/.test(attr)){attr=attr.toLowerCase();}dojo.attr(_1aa,attr,_1a7);break;case "innerHTML":_1aa.innerHTML=_1a7;break;case "class":dojo.removeClass(_1aa,this[attr]);dojo.addClass(_1aa,_1a7);break;}},this);this[attr]=_1a7;},attr:function(name,_1ad){var args=arguments.length;if(args==1&&!dojo.isString(name)){for(var x in name){this.attr(x,name[x]);}return this;}var _1b0=this._getAttrNames(name);if(args==2){if(this[_1b0.s]){return this[_1b0.s](_1ad)||this;}else{if(name in this.attributeMap){this._attrToDom(name,_1ad);}this[name]=_1ad;}return this;}else{if(this[_1b0.g]){return this[_1b0.g]();}else{return this[name];}}},_attrPairNames:{},_getAttrNames:function(name){var apn=this._attrPairNames;if(apn[name]){return apn[name];}var uc=name.charAt(0).toUpperCase()+name.substr(1);return apn[name]={n:name+"Node",s:"_set"+uc+"Attr",g:"_get"+uc+"Attr"};},toString:function(){return "[Widget "+this.declaredClass+", "+(this.id||"NO ID")+"]";},getDescendants:function(){if(this.containerNode){var list=dojo.query("[widgetId]",this.containerNode);return list.map(dijit.byNode);}else{return [];}},getChildren:function(){if(this.containerNode){return dijit.findWidgets(this.containerNode);}else{return [];}},nodesWithKeyClick:["input","button"],connect:function(obj,_1b6,_1b7){var d=dojo;var dc=dojo.connect;var _1ba=[];if(_1b6=="ondijitclick"){if(!this.nodesWithKeyClick[obj.nodeName]){var m=d.hitch(this,_1b7);_1ba.push(dc(obj,"onkeydown",this,function(e){if(!d.isFF&&e.keyCode==d.keys.ENTER&&!e.ctrlKey&&!e.shiftKey&&!e.altKey&&!e.metaKey){return m(e);}else{if(e.keyCode==d.keys.SPACE){d.stopEvent(e);}}}),dc(obj,"onkeyup",this,function(e){if(e.keyCode==d.keys.SPACE&&!e.ctrlKey&&!e.shiftKey&&!e.altKey&&!e.metaKey){return m(e);}}));if(d.isFF){_1ba.push(dc(obj,"onkeypress",this,function(e){if(e.keyCode==d.keys.ENTER&&!e.ctrlKey&&!e.shiftKey&&!e.altKey&&!e.metaKey){return m(e);}}));}}_1b6="onclick";}_1ba.push(dc(obj,_1b6,this,_1b7));this._connects.push(_1ba);return _1ba;},disconnect:function(_1bf){for(var i=0;i<this._connects.length;i++){if(this._connects[i]==_1bf){dojo.forEach(_1bf,dojo.disconnect);this._connects.splice(i,1);return;}}},isLeftToRight:function(){return dojo._isBodyLtr();},isFocusable:function(){return this.focus&&(dojo.style(this.domNode,"display")!="none");},placeAt:function(_1c1,_1c2){if(_1c1["declaredClass"]&&_1c1["addChild"]){_1c1.addChild(this,_1c2);}else{dojo.place(this.domNode,_1c1,_1c2);}return this;}});})();}if(!dojo._hasResource["dojo.string"]){dojo._hasResource["dojo.string"]=true;dojo.provide("dojo.string");dojo.string.rep=function(str,num){if(num<=0||!str){return "";}var buf=[];for(;;){if(num&1){buf.push(str);}if(!(num>>=1)){break;}str+=str;}return buf.join("");};dojo.string.pad=function(text,size,ch,end){if(!ch){ch="0";}var out=String(text),pad=dojo.string.rep(ch,Math.ceil((size-out.length)/ch.length));return end?out+pad:pad+out;};dojo.string.substitute=function(_1cc,map,_1ce,_1cf){_1cf=_1cf||dojo.global;_1ce=(!_1ce)?function(v){return v;}:dojo.hitch(_1cf,_1ce);return _1cc.replace(/\$\{([^\s\:\}]+)(?:\:([^\s\:\}]+))?\}/g,function(_1d1,key,_1d3){var _1d4=dojo.getObject(key,false,map);if(_1d3){_1d4=dojo.getObject(_1d3,false,_1cf).call(_1cf,_1d4,key);}return _1ce(_1d4,key).toString();});};dojo.string.trim=String.prototype.trim?dojo.trim:function(str){str=str.replace(/^\s+/,"");for(var i=str.length-1;i>=0;i--){if(/\S/.test(str.charAt(i))){str=str.substring(0,i+1);break;}}return str;};}if(!dojo._hasResource["dijit._Templated"]){dojo._hasResource["dijit._Templated"]=true;dojo.provide("dijit._Templated");dojo.declare("dijit._Templated",null,{templateString:null,templatePath:null,widgetsInTemplate:false,_skipNodeCache:false,_stringRepl:function(tmpl){var _1d8=this.declaredClass,_1d9=this;return dojo.string.substitute(tmpl,this,function(_1da,key){if(key.charAt(0)=="!"){_1da=dojo.getObject(key.substr(1),false,_1d9);}if(typeof _1da=="undefined"){throw new Error(_1d8+" template:"+key);}if(_1da==null){return "";}return key.charAt(0)=="!"?_1da:_1da.toString().replace(/"/g,""");},this);},buildRendering:function(){var _1dc=dijit._Templated.getCachedTemplate(this.templatePath,this.templateString,this._skipNodeCache);var node;if(dojo.isString(_1dc)){node=dojo._toDom(this._stringRepl(_1dc));}else{node=_1dc.cloneNode(true);}this.domNode=node;this._attachTemplateNodes(node);if(this.widgetsInTemplate){var cw=(this._supportingWidgets=dojo.parser.parse(node));this._attachTemplateNodes(cw,function(n,p){return n[p];});}this._fillContent(this.srcNodeRef);},_fillContent:function(_1e1){var dest=this.containerNode;if(_1e1&&dest){while(_1e1.hasChildNodes()){dest.appendChild(_1e1.firstChild);}}},_attachTemplateNodes:function(_1e3,_1e4){_1e4=_1e4||function(n,p){return n.getAttribute(p);};var _1e7=dojo.isArray(_1e3)?_1e3:(_1e3.all||_1e3.getElementsByTagName("*"));var x=dojo.isArray(_1e3)?0:-1;for(;x<_1e7.length;x++){var _1e9=(x==-1)?_1e3:_1e7[x];if(this.widgetsInTemplate&&_1e4(_1e9,"dojoType")){continue;}var _1ea=_1e4(_1e9,"dojoAttachPoint");if(_1ea){var _1eb,_1ec=_1ea.split(/\s*,\s*/);while((_1eb=_1ec.shift())){if(dojo.isArray(this[_1eb])){this[_1eb].push(_1e9);}else{this[_1eb]=_1e9;}}}var _1ed=_1e4(_1e9,"dojoAttachEvent");if(_1ed){var _1ee,_1ef=_1ed.split(/\s*,\s*/);var trim=dojo.trim;while((_1ee=_1ef.shift())){if(_1ee){var _1f1=null;if(_1ee.indexOf(":")!=-1){var _1f2=_1ee.split(":");_1ee=trim(_1f2[0]);_1f1=trim(_1f2[1]);}else{_1ee=trim(_1ee);}if(!_1f1){_1f1=_1ee;}this.connect(_1e9,_1ee,_1f1);}}}var role=_1e4(_1e9,"waiRole");if(role){dijit.setWaiRole(_1e9,role);}var _1f4=_1e4(_1e9,"waiState");if(_1f4){dojo.forEach(_1f4.split(/\s*,\s*/),function(_1f5){if(_1f5.indexOf("-")!=-1){var pair=_1f5.split("-");dijit.setWaiState(_1e9,pair[0],pair[1]);}});}}}});dijit._Templated._templateCache={};dijit._Templated.getCachedTemplate=function(_1f7,_1f8,_1f9){var _1fa=dijit._Templated._templateCache;var key=_1f8||_1f7;var _1fc=_1fa[key];if(_1fc){if(!_1fc.ownerDocument||_1fc.ownerDocument==dojo.doc){return _1fc;}dojo.destroy(_1fc);}if(!_1f8){_1f8=dijit._Templated._sanitizeTemplateString(dojo.trim(dojo._getText(_1f7)));}_1f8=dojo.string.trim(_1f8);if(_1f9||_1f8.match(/\$\{([^\}]+)\}/g)){return (_1fa[key]=_1f8);}else{return (_1fa[key]=dojo._toDom(_1f8));}};dijit._Templated._sanitizeTemplateString=function(_1fd){if(_1fd){_1fd=_1fd.replace(/^\s*<\?xml(\s)+version=[\'\"](\d)*.(\d)*[\'\"](\s)*\?>/im,"");var _1fe=_1fd.match(/<body[^>]*>\s*([\s\S]+)\s*<\/body>/im);if(_1fe){_1fd=_1fe[1];}}else{_1fd="";}return _1fd;};if(dojo.isIE){dojo.addOnWindowUnload(function(){var _1ff=dijit._Templated._templateCache;for(var key in _1ff){var _201=_1ff[key];if(!isNaN(_201.nodeType)){dojo.destroy(_201);}delete _1ff[key];}});}dojo.extend(dijit._Widget,{dojoAttachEvent:"",dojoAttachPoint:"",waiRole:"",waiState:""});}if(!dojo._hasResource["dijit._Container"]){dojo._hasResource["dijit._Container"]=true;dojo.provide("dijit._Container");dojo.declare("dijit._Container",null,{isContainer:true,buildRendering:function(){this.inherited(arguments);if(!this.containerNode){this.containerNode=this.domNode;}},addChild:function(_202,_203){var _204=this.containerNode;if(_203&&typeof _203=="number"){var _205=this.getChildren();if(_205&&_205.length>=_203){_204=_205[_203-1].domNode;_203="after";}}dojo.place(_202.domNode,_204,_203);if(this._started&&!_202._started){_202.startup();}},removeChild:function(_206){if(typeof _206=="number"&&_206>0){_206=this.getChildren()[_206];}if(!_206||!_206.domNode){return;}var node=_206.domNode;node.parentNode.removeChild(node);},_nextElement:function(node){do{node=node.nextSibling;}while(node&&node.nodeType!=1);return node;},_firstElement:function(node){node=node.firstChild;if(node&&node.nodeType!=1){node=this._nextElement(node);}return node;},getChildren:function(){return dojo.query("> [widgetId]",this.containerNode).map(dijit.byNode);},hasChildren:function(){return !!this._firstElement(this.containerNode);},destroyDescendants:function(_20a){dojo.forEach(this.getChildren(),function(_20b){_20b.destroyRecursive(_20a);});},_getSiblingOfChild:function(_20c,dir){var node=_20c.domNode;var _20f=(dir>0?"nextSibling":"previousSibling");do{node=node[_20f];}while(node&&(node.nodeType!=1||!dijit.byNode(node)));return node?dijit.byNode(node):null;},getIndexOfChild:function(_210){var _211=this.getChildren();for(var i=0,c;c=_211[i];i++){if(c==_210){return i;}}return -1;}});}if(!dojo._hasResource["dijit._Contained"]){dojo._hasResource["dijit._Contained"]=true;dojo.provide("dijit._Contained");dojo.declare("dijit._Contained",null,{getParent:function(){for(var p=this.domNode.parentNode;p;p=p.parentNode){var id=p.getAttribute&&p.getAttribute("widgetId");if(id){var _216=dijit.byId(id);return _216.isContainer?_216:null;}}return null;},_getSibling:function(_217){var node=this.domNode;do{node=node[_217+"Sibling"];}while(node&&node.nodeType!=1);if(!node){return null;}var id=node.getAttribute("widgetId");return dijit.byId(id);},getPreviousSibling:function(){return this._getSibling("previous");},getNextSibling:function(){return this._getSibling("next");},getIndexInParent:function(){var p=this.getParent();if(!p||!p.getIndexOfChild){return -1;}return p.getIndexOfChild(this);}});}if(!dojo._hasResource["dijit.layout._LayoutWidget"]){dojo._hasResource["dijit.layout._LayoutWidget"]=true;dojo.provide("dijit.layout._LayoutWidget");dojo.declare("dijit.layout._LayoutWidget",[dijit._Widget,dijit._Container,dijit._Contained],{baseClass:"dijitLayoutContainer",isLayoutContainer:true,postCreate:function(){dojo.addClass(this.domNode,"dijitContainer");dojo.addClass(this.domNode,this.baseClass);},startup:function(){if(this._started){return;}dojo.forEach(this.getChildren(),function(_21b){_21b.startup();});if(!this.getParent||!this.getParent()){this.resize();this._viewport=dijit.getViewport();this.connect(dojo.global,"onresize",function(){var _21c=dijit.getViewport();if(_21c.w!=this._viewport.w||_21c.h!=this._viewport.h){this._viewport=_21c;this.resize();}});}this.inherited(arguments);},resize:function(_21d,_21e){var node=this.domNode;if(_21d){dojo.marginBox(node,_21d);if(_21d.t){node.style.top=_21d.t+"px";}if(_21d.l){node.style.left=_21d.l+"px";}}var mb=_21e||{};dojo.mixin(mb,_21d||{});if(!("h" in mb)||!("w" in mb)){mb=dojo.mixin(dojo.marginBox(node),mb);}var cs=dojo.getComputedStyle(node);var me=dojo._getMarginExtents(node,cs);var be=dojo._getBorderExtents(node,cs);var bb=(this._borderBox={w:mb.w-(me.w+be.w),h:mb.h-(me.h+be.h)});var pe=dojo._getPadExtents(node,cs);this._contentBox={l:dojo._toPixelValue(node,cs.paddingLeft),t:dojo._toPixelValue(node,cs.paddingTop),w:bb.w-pe.w,h:bb.h-pe.h};this.layout();},layout:function(){},_setupChild:function(_226){dojo.addClass(_226.domNode,this.baseClass+"-child");if(_226.baseClass){dojo.addClass(_226.domNode,this.baseClass+"-"+_226.baseClass);}},addChild:function(_227,_228){this.inherited(arguments);if(this._started){this._setupChild(_227);}},removeChild:function(_229){dojo.removeClass(_229.domNode,this.baseClass+"-child");if(_229.baseClass){dojo.removeClass(_229.domNode,this.baseClass+"-"+_229.baseClass);}this.inherited(arguments);}});dijit.layout.marginBox2contentBox=function(node,mb){var cs=dojo.getComputedStyle(node);var me=dojo._getMarginExtents(node,cs);var pb=dojo._getPadBorderExtents(node,cs);return {l:dojo._toPixelValue(node,cs.paddingLeft),t:dojo._toPixelValue(node,cs.paddingTop),w:mb.w-(me.w+pb.w),h:mb.h-(me.h+pb.h)};};(function(){var _22f=function(word){return word.substring(0,1).toUpperCase()+word.substring(1);};var size=function(_232,dim){_232.resize?_232.resize(dim):dojo.marginBox(_232.domNode,dim);dojo.mixin(_232,dojo.marginBox(_232.domNode));dojo.mixin(_232,dim);};dijit.layout.layoutChildren=function(_234,dim,_236){dim=dojo.mixin({},dim);dojo.addClass(_234,"dijitLayoutContainer");_236=dojo.filter(_236,function(item){return item.layoutAlign!="client";}).concat(dojo.filter(_236,function(item){return item.layoutAlign=="client";}));dojo.forEach(_236,function(_239){var elm=_239.domNode,pos=_239.layoutAlign;var _23c=elm.style;_23c.left=dim.l+"px";_23c.top=dim.t+"px";_23c.bottom=_23c.right="auto";dojo.addClass(elm,"dijitAlign"+_22f(pos));if(pos=="top"||pos=="bottom"){size(_239,{w:dim.w});dim.h-=_239.h;if(pos=="top"){dim.t+=_239.h;}else{_23c.top=dim.t+dim.h+"px";}}else{if(pos=="left"||pos=="right"){size(_239,{h:dim.h});dim.w-=_239.w;if(pos=="left"){dim.l+=_239.w;}else{_23c.left=dim.l+dim.w+"px";}}else{if(pos=="client"){size(_239,dim);}}}});};})();}if(!dojo._hasResource["dijit.form._FormWidget"]){dojo._hasResource["dijit.form._FormWidget"]=true;dojo.provide("dijit.form._FormWidget");dojo.declare("dijit.form._FormWidget",[dijit._Widget,dijit._Templated],{baseClass:"",name:"",alt:"",value:"",type:"text",tabIndex:"0",disabled:false,readOnly:false,intermediateChanges:false,scrollOnFocus:true,attributeMap:dojo.delegate(dijit._Widget.prototype.attributeMap,{value:"focusNode",disabled:"focusNode",readOnly:"focusNode",id:"focusNode",tabIndex:"focusNode",alt:"focusNode"}),postMixInProperties:function(){this.nameAttrSetting=this.name?("name='"+this.name+"'"):"";this.inherited(arguments);},_setDisabledAttr:function(_23d){this.disabled=_23d;dojo.attr(this.focusNode,"disabled",_23d);dijit.setWaiState(this.focusNode,"disabled",_23d);if(_23d){this._hovering=false;this._active=false;this.focusNode.removeAttribute("tabIndex");}else{this.focusNode.setAttribute("tabIndex",this.tabIndex);}this._setStateClass();},setDisabled:function(_23e){dojo.deprecated("setDisabled("+_23e+") is deprecated. Use attr('disabled',"+_23e+") instead.","","2.0");this.attr("disabled",_23e);},_onFocus:function(e){if(this.scrollOnFocus){dijit.scrollIntoView(this.domNode);}this.inherited(arguments);},_onMouse:function(_240){var _241=_240.currentTarget;if(_241&&_241.getAttribute){this.stateModifier=_241.getAttribute("stateModifier")||"";}if(!this.disabled){switch(_240.type){case "mouseenter":case "mouseover":this._hovering=true;this._active=this._mouseDown;break;case "mouseout":case "mouseleave":this._hovering=false;this._active=false;break;case "mousedown":this._active=true;this._mouseDown=true;var _242=this.connect(dojo.body(),"onmouseup",function(){if(this._mouseDown&&this.isFocusable()){this.focus();}this._active=false;this._mouseDown=false;this._setStateClass();this.disconnect(_242);});break;}this._setStateClass();}},isFocusable:function(){return !this.disabled&&!this.readOnly&&this.focusNode&&(dojo.style(this.domNode,"display")!="none");},focus:function(){dijit.focus(this.focusNode);},_setStateClass:function(){var _243=this.baseClass.split(" ");function _244(_245){_243=_243.concat(dojo.map(_243,function(c){return c+_245;}),"dijit"+_245);};if(this.checked){_244("Checked");}if(this.state){_244(this.state);}if(this.selected){_244("Selected");}if(this.disabled){_244("Disabled");}else{if(this.readOnly){_244("ReadOnly");}else{if(this._active){_244(this.stateModifier+"Active");}else{if(this._focused){_244("Focused");}if(this._hovering){_244(this.stateModifier+"Hover");}}}}var tn=this.stateNode||this.domNode,_248={};dojo.forEach(tn.className.split(" "),function(c){_248[c]=true;});if("_stateClasses" in this){dojo.forEach(this._stateClasses,function(c){delete _248[c];});}dojo.forEach(_243,function(c){_248[c]=true;});var _24c=[];for(var c in _248){_24c.push(c);}tn.className=_24c.join(" ");this._stateClasses=_243;},compare:function(val1,val2){if((typeof val1=="number")&&(typeof val2=="number")){return (isNaN(val1)&&isNaN(val2))?0:(val1-val2);}else{if(val1>val2){return 1;}else{if(val1<val2){return -1;}else{return 0;}}}},onChange:function(_250){},_onChangeActive:false,_handleOnChange:function(_251,_252){this._lastValue=_251;if(this._lastValueReported==undefined&&(_252===null||!this._onChangeActive)){this._resetValue=this._lastValueReported=_251;}if((this.intermediateChanges||_252||_252===undefined)&&((typeof _251!=typeof this._lastValueReported)||this.compare(_251,this._lastValueReported)!=0)){this._lastValueReported=_251;if(this._onChangeActive){this.onChange(_251);}}},create:function(){this.inherited(arguments);this._onChangeActive=true;this._setStateClass();},destroy:function(){if(this._layoutHackHandle){clearTimeout(this._layoutHackHandle);}this.inherited(arguments);},setValue:function(_253){dojo.deprecated("dijit.form._FormWidget:setValue("+_253+") is deprecated. Use attr('value',"+_253+") instead.","","2.0");this.attr("value",_253);},getValue:function(){dojo.deprecated(this.declaredClass+"::getValue() is deprecated. Use attr('value') instead.","","2.0");return this.attr("value");},_layoutHack:function(){if(dojo.isFF==2&&!this._layoutHackHandle){var node=this.domNode;var old=node.style.opacity;node.style.opacity="0.999";this._layoutHackHandle=setTimeout(dojo.hitch(this,function(){this._layoutHackHandle=null;node.style.opacity=old;}),0);}}});dojo.declare("dijit.form._FormValueWidget",dijit.form._FormWidget,{attributeMap:dojo.delegate(dijit.form._FormWidget.prototype.attributeMap,{value:""}),postCreate:function(){if(dojo.isIE||dojo.isWebKit){this.connect(this.focusNode||this.domNode,"onkeydown",this._onKeyDown);}if(this._resetValue===undefined){this._resetValue=this.value;}},_setValueAttr:function(_256,_257){this.value=_256;this._handleOnChange(_256,_257);},_getValueAttr:function(_258){return this._lastValue;},undo:function(){this._setValueAttr(this._lastValueReported,false);},reset:function(){this._hasBeenBlurred=false;this._setValueAttr(this._resetValue,true);},_onKeyDown:function(e){if(e.keyCode==dojo.keys.ESCAPE&&!e.ctrlKey&&!e.altKey){var te;if(dojo.isIE){e.preventDefault();te=document.createEventObject();te.keyCode=dojo.keys.ESCAPE;te.shiftKey=e.shiftKey;e.srcElement.fireEvent("onkeypress",te);}else{if(dojo.isWebKit){te=document.createEvent("Events");te.initEvent("keypress",true,true);te.keyCode=dojo.keys.ESCAPE;te.shiftKey=e.shiftKey;e.target.dispatchEvent(te);}}}}});}if(!dojo._hasResource["dijit.dijit"]){dojo._hasResource["dijit.dijit"]=true;dojo.provide("dijit.dijit");} Property changes on: branches/vhffs-design/vhffs-panel/js/dijit/dijit.js ___________________________________________________________________ Name: svn:mergeinfo + Added: branches/vhffs-design/vhffs-panel/js/dijit/form/TextBox.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/form/TextBox.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dijit/form/TextBox.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,152 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + + +if(!dojo._hasResource["dijit.form.TextBox"]){ +dojo._hasResource["dijit.form.TextBox"]=true; +dojo.provide("dijit.form.TextBox"); +dojo.require("dijit.form._FormWidget"); +dojo.declare("dijit.form.TextBox",dijit.form._FormValueWidget,{trim:false,uppercase:false,lowercase:false,propercase:false,maxLength:"",templateString:"<input class=\"dijit dijitReset dijitLeft\" dojoAttachPoint='textbox,focusNode'\n\tdojoAttachEvent='onmouseenter:_onMouse,onmouseleave:_onMouse'\n\tautocomplete=\"off\" type=\"${type}\" ${nameAttrSetting}\n\t/>\n",baseClass:"dijitTextBox",attributeMap:dojo.delegate(dijit.form._FormValueWidget.prototype.attributeMap,{maxLength:"focusNode"}),_getValueAttr:function(){ +return this.parse(this.attr("displayedValue"),this.constraints); +},_setValueAttr:function(_1,_2,_3){ +var _4; +if(_1!==undefined){ +_4=this.filter(_1); +if(typeof _3!="string"){ +if(_4!==null&&((typeof _4!="number")||!isNaN(_4))){ +_3=this.filter(this.format(_4,this.constraints)); +}else{ +_3=""; +} +} +} +if(_3!=null&&_3!=undefined&&((typeof _3)!="number"||!isNaN(_3))&&this.textbox.value!=_3){ +this.textbox.value=_3; +} +this.inherited(arguments,[_4,_2]); +},displayedValue:"",getDisplayedValue:function(){ +dojo.deprecated(this.declaredClass+"::getDisplayedValue() is deprecated. Use attr('displayedValue') instead.","","2.0"); +return this.attr("displayedValue"); +},_getDisplayedValueAttr:function(){ +return this.filter(this.textbox.value); +},setDisplayedValue:function(_5){ +dojo.deprecated(this.declaredClass+"::setDisplayedValue() is deprecated. Use attr('displayedValue', ...) instead.","","2.0"); +this.attr("displayedValue",_5); +},_setDisplayedValueAttr:function(_6){ +if(_6===null||_6===undefined){ +_6=""; +}else{ +if(typeof _6!="string"){ +_6=String(_6); +} +} +this.textbox.value=_6; +this._setValueAttr(this.attr("value"),undefined,_6); +},format:function(_7,_8){ +return ((_7==null||_7==undefined)?"":(_7.toString?_7.toString():_7)); +},parse:function(_9,_a){ +return _9; +},_refreshState:function(){ +},_onInput:function(e){ +if(e&&e.type&&/key/i.test(e.type)&&e.keyCode){ +switch(e.keyCode){ +case dojo.keys.SHIFT: +case dojo.keys.ALT: +case dojo.keys.CTRL: +case dojo.keys.TAB: +return; +} +} +if(this.intermediateChanges){ +var _c=this; +setTimeout(function(){ +_c._handleOnChange(_c.attr("value"),false); +},0); +} +this._refreshState(); +},postCreate:function(){ +this.textbox.setAttribute("value",this.textbox.value); +this.inherited(arguments); +if(dojo.isMoz||dojo.isOpera){ +this.connect(this.textbox,"oninput",this._onInput); +}else{ +this.connect(this.textbox,"onkeydown",this._onInput); +this.connect(this.textbox,"onkeyup",this._onInput); +this.connect(this.textbox,"onpaste",this._onInput); +this.connect(this.textbox,"oncut",this._onInput); +} +this._layoutHack(); +},_blankValue:"",filter:function(_d){ +if(_d===null){ +return this._blankValue; +} +if(typeof _d!="string"){ +return _d; +} +if(this.trim){ +_d=dojo.trim(_d); +} +if(this.uppercase){ +_d=_d.toUpperCase(); +} +if(this.lowercase){ +_d=_d.toLowerCase(); +} +if(this.propercase){ +_d=_d.replace(/[^\s]+/g,function(_e){ +return _e.substring(0,1).toUpperCase()+_e.substring(1); +}); +} +return _d; +},_setBlurValue:function(){ +this._setValueAttr(this.attr("value"),true); +},_onBlur:function(e){ +if(this.disabled){ +return; +} +this._setBlurValue(); +this.inherited(arguments); +},_onFocus:function(e){ +if(this.disabled){ +return; +} +this._refreshState(); +this.inherited(arguments); +},reset:function(){ +this.textbox.value=""; +this.inherited(arguments); +}}); +dijit.selectInputText=function(_11,_12,_13){ +var _14=dojo.global; +var _15=dojo.doc; +_11=dojo.byId(_11); +if(isNaN(_12)){ +_12=0; +} +if(isNaN(_13)){ +_13=_11.value?_11.value.length:0; +} +_11.focus(); +if(_15["selection"]&&dojo.body()["createTextRange"]){ +if(_11.createTextRange){ +var _16=_11.createTextRange(); +with(_16){ +collapse(true); +moveStart("character",_12); +moveEnd("character",_13); +select(); +} +} +}else{ +if(_14["getSelection"]){ +var _17=_14.getSelection(); +if(_11.setSelectionRange){ +_11.setSelectionRange(_12,_13); +} +} +} +}; +} Added: branches/vhffs-design/vhffs-panel/js/dijit/form/ValidationTextBox.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/form/ValidationTextBox.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dijit/form/ValidationTextBox.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,207 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + + +if(!dojo._hasResource["dijit.form.ValidationTextBox"]){ +dojo._hasResource["dijit.form.ValidationTextBox"]=true; +dojo.provide("dijit.form.ValidationTextBox"); +dojo.require("dojo.i18n"); +dojo.require("dijit.form.TextBox"); +dojo.require("dijit.Tooltip"); +dojo.requireLocalization("dijit.form","validate",null,"ROOT,ar,ca,cs,da,de,el,es,fi,fr,he,hu,it,ja,ko,nb,nl,pl,pt,pt-pt,ru,sk,sl,sv,th,tr,zh,zh-tw"); +dojo.declare("dijit.form.ValidationTextBox",dijit.form.TextBox,{templateString:"<div class=\"dijit dijitReset dijitInlineTable dijitLeft\"\n\tid=\"widget_${id}\"\n\tdojoAttachEvent=\"onmouseenter:_onMouse,onmouseleave:_onMouse,onmousedown:_onMouse\" waiRole=\"presentation\"\n\t><div style=\"overflow:hidden;\"\n\t\t><div class=\"dijitReset dijitValidationIcon\"><br></div\n\t\t><div class=\"dijitReset dijitValidationIconText\">Χ</div\n\t\t><div class=\"dijitReset dijitInputField\"\n\t\t\t><input class=\"dijitReset\" dojoAttachPoint='textbox,focusNode' autocomplete=\"off\"\n\t\t\t${nameAttrSetting} type='${type}'\n\t\t/></div\n\t></div\n></div>\n",baseClass:"dijitTextBox",required:false,promptMessage:"",invalidMessage:"$_unset_$",constraints:{},regExp:".*",regExpGen:function(_1){ +return this.regExp; +},state:"",tooltipPosition:[],_setValueAttr:function(){ +this.inherited(arguments); +this.validate(this._focused); +},validator:function(_2,_3){ +return (new RegExp("^(?:"+this.regExpGen(_3)+")"+(this.required?"":"?")+"$")).test(_2)&&(!this.required||!this._isEmpty(_2))&&(this._isEmpty(_2)||this.parse(_2,_3)!==undefined); +},_isValidSubset:function(){ +return this.textbox.value.search(this._partialre)==0; +},isValid:function(_4){ +return this.validator(this.textbox.value,this.constraints); +},_isEmpty:function(_5){ +return /^\s*$/.test(_5); +},getErrorMessage:function(_6){ +return this.invalidMessage; +},getPromptMessage:function(_7){ +return this.promptMessage; +},_maskValidSubsetError:true,validate:function(_8){ +var _9=""; +var _a=this.disabled||this.isValid(_8); +if(_a){ +this._maskValidSubsetError=true; +} +var _b=!_a&&_8&&this._isValidSubset(); +var _c=this._isEmpty(this.textbox.value); +this.state=(_a||(!this._hasBeenBlurred&&_c)||_b)?"":"Error"; +if(this.state=="Error"){ +this._maskValidSubsetError=false; +} +this._setStateClass(); +dijit.setWaiState(this.focusNode,"invalid",_a?"false":"true"); +if(_8){ +if(_c){ +_9=this.getPromptMessage(true); +} +if(!_9&&(this.state=="Error"||(_b&&!this._maskValidSubsetError))){ +_9=this.getErrorMessage(true); +} +} +this.displayMessage(_9); +return _a; +},_message:"",displayMessage:function(_d){ +if(this._message==_d){ +return; +} +this._message=_d; +dijit.hideTooltip(this.domNode); +if(_d){ +dijit.showTooltip(_d,this.domNode,this.tooltipPosition); +} +},_refreshState:function(){ +this.validate(this._focused); +this.inherited(arguments); +},constructor:function(){ +this.constraints={}; +},postMixInProperties:function(){ +this.inherited(arguments); +this.constraints.locale=this.lang; +this.messages=dojo.i18n.getLocalization("dijit.form","validate",this.lang); +if(this.invalidMessage=="$_unset_$"){ +this.invalidMessage=this.messages.invalidMessage; +} +var p=this.regExpGen(this.constraints); +this.regExp=p; +var _f=""; +if(p!=".*"){ +this.regExp.replace(/\\.|\[\]|\[.*?[^\\]{1}\]|\{.*?\}|\(\?[=:!]|./g,function(re){ +switch(re.charAt(0)){ +case "{": +case "+": +case "?": +case "*": +case "^": +case "$": +case "|": +case "(": +_f+=re; +break; +case ")": +_f+="|$)"; +break; +default: +_f+="(?:"+re+"|$)"; +break; +} +}); +} +try{ +"".search(_f); +} +catch(e){ +_f=this.regExp; +console.warn("RegExp error in "+this.declaredClass+": "+this.regExp); +} +this._partialre="^(?:"+_f+")$"; +},_setDisabledAttr:function(_11){ +this.inherited(arguments); +if(this.valueNode){ +this.valueNode.disabled=_11; +} +this._refreshState(); +},_setRequiredAttr:function(_12){ +this.required=_12; +dijit.setWaiState(this.focusNode,"required",_12); +this._refreshState(); +},postCreate:function(){ +if(dojo.isIE){ +var s=dojo.getComputedStyle(this.focusNode); +if(s){ +var ff=s.fontFamily; +if(ff){ +this.focusNode.style.fontFamily=ff; +} +} +} +this.inherited(arguments); +},reset:function(){ +this._maskValidSubsetError=true; +this.inherited(arguments); +}}); +dojo.declare("dijit.form.MappedTextBox",dijit.form.ValidationTextBox,{postMixInProperties:function(){ +this.inherited(arguments); +this.nameAttrSetting=""; +},serialize:function(val,_16){ +return val.toString?val.toString():""; +},toString:function(){ +var val=this.filter(this.attr("value")); +return val!=null?(typeof val=="string"?val:this.serialize(val,this.constraints)):""; +},validate:function(){ +this.valueNode.value=this.toString(); +return this.inherited(arguments); +},buildRendering:function(){ +this.inherited(arguments); +this.valueNode=dojo.create("input",{style:{display:"none"},type:this.type,name:this.name},this.textbox,"after"); +},_setDisabledAttr:function(_18){ +this.inherited(arguments); +dojo.attr(this.valueNode,"disabled",_18); +},reset:function(){ +this.valueNode.value=""; +this.inherited(arguments); +}}); +dojo.declare("dijit.form.RangeBoundTextBox",dijit.form.MappedTextBox,{rangeMessage:"",rangeCheck:function(_19,_1a){ +var _1b="min" in _1a; +var _1c="max" in _1a; +if(_1b||_1c){ +return (!_1b||this.compare(_19,_1a.min)>=0)&&(!_1c||this.compare(_19,_1a.max)<=0); +} +return true; +},isInRange:function(_1d){ +return this.rangeCheck(this.attr("value"),this.constraints); +},_isDefinitelyOutOfRange:function(){ +var val=this.attr("value"); +var _1f=false; +var _20=false; +if("min" in this.constraints){ +var min=this.constraints.min; +val=this.compare(val,((typeof min=="number")&&min>=0&&val!=0)?0:min); +_1f=(typeof val=="number")&&val<0; +} +if("max" in this.constraints){ +var max=this.constraints.max; +val=this.compare(val,((typeof max!="number")||max>0)?max:0); +_20=(typeof val=="number")&&val>0; +} +return _1f||_20; +},_isValidSubset:function(){ +return this.inherited(arguments)&&!this._isDefinitelyOutOfRange(); +},isValid:function(_23){ +return this.inherited(arguments)&&((this._isEmpty(this.textbox.value)&&!this.required)||this.isInRange(_23)); +},getErrorMessage:function(_24){ +if(dijit.form.RangeBoundTextBox.superclass.isValid.call(this,false)&&!this.isInRange(_24)){ +return this.rangeMessage; +} +return this.inherited(arguments); +},postMixInProperties:function(){ +this.inherited(arguments); +if(!this.rangeMessage){ +this.messages=dojo.i18n.getLocalization("dijit.form","validate",this.lang); +this.rangeMessage=this.messages.rangeMessage; +} +},postCreate:function(){ +this.inherited(arguments); +if(this.constraints.min!==undefined){ +dijit.setWaiState(this.focusNode,"valuemin",this.constraints.min); +} +if(this.constraints.max!==undefined){ +dijit.setWaiState(this.focusNode,"valuemax",this.constraints.max); +} +},_setValueAttr:function(_25,_26){ +dijit.setWaiState(this.focusNode,"valuenow",_25); +this.inherited(arguments); +}}); +} Added: branches/vhffs-design/vhffs-panel/js/dijit/form/nls/validate.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dijit/form/nls/validate.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dijit/form/nls/validate.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1 @@ +({"rangeMessage":"This value is out of range.","invalidMessage":"The value entered is not valid.","missingMessage":"This value is required."}) \ No newline at end of file Modified: branches/vhffs-design/vhffs-panel/js/dojo/back.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/back.js 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/js/dojo/back.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,394 +1,254 @@ -if(!dojo._hasResource["dojo.back"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo.back"] = true; -dojo.provide("dojo.back"); +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ -/*===== -dojo.back = { - // summary: Browser history management resources -} -=====*/ - -(function(){ - var back = dojo.back; - - // everyone deals with encoding the hash slightly differently - - function getHash(){ - var h = window.location.hash; - if(h.charAt(0) == "#"){ h = h.substring(1); } - return dojo.isMozilla ? h : decodeURIComponent(h); - } - - function setHash(h){ - if(!h){ h = ""; } - window.location.hash = encodeURIComponent(h); - historyCounter = history.length; - } - - // if we're in the test for these methods, expose them on dojo.back. ok'd with alex. - if(dojo.exists("tests.back-hash")){ - back.getHash = getHash; - back.setHash = setHash; - } - - var initialHref = (typeof(window) !== "undefined") ? window.location.href : ""; - var initialHash = (typeof(window) !== "undefined") ? getHash() : ""; - var initialState = null; - - var locationTimer = null; - var bookmarkAnchor = null; - var historyIframe = null; - var forwardStack = []; - var historyStack = []; - var moveForward = false; - var changingUrl = false; - var historyCounter; - - function handleBackButton(){ - //summary: private method. Do not call this directly. - - //The "current" page is always at the top of the history stack. - //console.debug("handlingBackButton"); - var current = historyStack.pop(); - if(!current){ return; } - var last = historyStack[historyStack.length-1]; - if(!last && historyStack.length == 0){ - last = initialState; - } - if(last){ - if(last.kwArgs["back"]){ - last.kwArgs["back"](); - }else if(last.kwArgs["backButton"]){ - last.kwArgs["backButton"](); - }else if(last.kwArgs["handle"]){ - last.kwArgs.handle("back"); - } - } - forwardStack.push(current); - //console.debug("done handling back"); - } - - back.goBack = handleBackButton; - - function handleForwardButton(){ - //summary: private method. Do not call this directly. - //console.debug("handling forward"); - var last = forwardStack.pop(); - if(!last){ return; } - if(last.kwArgs["forward"]){ - last.kwArgs.forward(); - }else if(last.kwArgs["forwardButton"]){ - last.kwArgs.forwardButton(); - }else if(last.kwArgs["handle"]){ - last.kwArgs.handle("forward"); - } - historyStack.push(last); - //console.debug("done handling forward"); - } - - back.goForward = handleForwardButton; - - function createState(url, args, hash){ - //summary: private method. Do not call this directly. - return {"url": url, "kwArgs": args, "urlHash": hash}; //Object - } - - function getUrlQuery(url){ - //summary: private method. Do not call this directly. - var segments = url.split("?"); - if(segments.length < 2){ - return null; //null - } - else{ - return segments[1]; //String - } - } - - function loadIframeHistory(){ - //summary: private method. Do not call this directly. - var url = (dojo.config["dojoIframeHistoryUrl"] || dojo.moduleUrl("dojo", "resources/iframe_history.html")) + "?" + (new Date()).getTime(); - moveForward = true; - if(historyIframe){ - dojo.isSafari ? historyIframe.location = url : window.frames[historyIframe.name].location = url; - }else{ - //console.warn("dojo.back: Not initialised. You need to call dojo.back.init() from a <script> block that lives inside the <body> tag."); - } - return url; //String - } - - function checkLocation(){ - //console.debug("checking url"); - if(!changingUrl){ - var hsl = historyStack.length; - - var hash = getHash(); - - if((hash === initialHash||window.location.href == initialHref)&&(hsl == 1)){ - // FIXME: could this ever be a forward button? - // we can't clear it because we still need to check for forwards. Ugg. - // clearInterval(this.locationTimer); - handleBackButton(); - return; - } - - // first check to see if we could have gone forward. We always halt on - // a no-hash item. - if(forwardStack.length > 0){ - if(forwardStack[forwardStack.length-1].urlHash === hash){ - handleForwardButton(); - return; - } - } - - // ok, that didn't work, try someplace back in the history stack - if((hsl >= 2)&&(historyStack[hsl-2])){ - if(historyStack[hsl-2].urlHash === hash){ - handleBackButton(); - return; - } - } - - if(dojo.isSafari && dojo.isSafari < 3){ - var hisLen = history.length; - if(hisLen > historyCounter) handleForwardButton(); - else if(hisLen < historyCounter) handleBackButton(); - historyCounter = hisLen; - } - } - //console.debug("done checking"); - }; - - back.init = function(){ - //summary: Initializes the undo stack. This must be called from a <script> - // block that lives inside the <body> tag to prevent bugs on IE. - if(dojo.byId("dj_history")){ return; } // prevent reinit - var src = dojo.config["dojoIframeHistoryUrl"] || dojo.moduleUrl("dojo", "resources/iframe_history.html"); - document.write('<iframe style="border:0;width:1px;height:1px;position:absolute;visibility:hidden;bottom:0;right:0;" name="dj_history" id="dj_history" src="' + src + '"></iframe>'); - }; - - back.setInitialState = function(/*Object*/args){ - //summary: - // Sets the state object and back callback for the very first page - // that is loaded. - //description: - // It is recommended that you call this method as part of an event - // listener that is registered via dojo.addOnLoad(). - //args: Object - // See the addToHistory() function for the list of valid args properties. - initialState = createState(initialHref, args, initialHash); - }; - - //FIXME: Make these doc comments not be awful. At least they're not wrong. - //FIXME: Would like to support arbitrary back/forward jumps. Have to rework iframeLoaded among other things. - //FIXME: is there a slight race condition in moz using change URL with the timer check and when - // the hash gets set? I think I have seen a back/forward call in quick succession, but not consistent. - - - /*===== - dojo.__backArgs = function(kwArgs){ - // back: Function? - // A function to be called when this state is reached via the user - // clicking the back button. - // forward: Function? - // Upon return to this state from the "back, forward" combination - // of navigation steps, this function will be called. Somewhat - // analgous to the semantic of an "onRedo" event handler. - // changeUrl: Boolean?|String? - // Boolean indicating whether or not to create a unique hash for - // this state. If a string is passed instead, it is used as the - // hash. - } - =====*/ - - back.addToHistory = function(/*dojo.__backArgs*/ args){ - // summary: - // adds a state object (args) to the history list. - // description: - // To support getting back button notifications, the object - // argument should implement a function called either "back", - // "backButton", or "handle". The string "back" will be passed as - // the first and only argument to this callback. - // - // To support getting forward button notifications, the object - // argument should implement a function called either "forward", - // "forwardButton", or "handle". The string "forward" will be - // passed as the first and only argument to this callback. - // - // If you want the browser location string to change, define "changeUrl" on the object. If the - // value of "changeUrl" is true, then a unique number will be appended to the URL as a fragment - // identifier (http://some.domain.com/path#uniquenumber). If it is any other value that does - // not evaluate to false, that value will be used as the fragment identifier. For example, - // if changeUrl: 'page1', then the URL will look like: http://some.domain.com/path#page1 - // - // example: - // | dojo.back.addToHistory({ - // | back: function(){ console.debug('back pressed'); }, - // | forward: function(){ console.debug('forward pressed'); }, - // | changeUrl: true - // | }); - - // BROWSER NOTES: - // Safari 1.2: - // back button "works" fine, however it's not possible to actually - // DETECT that you've moved backwards by inspecting window.location. - // Unless there is some other means of locating. - // FIXME: perhaps we can poll on history.length? - // Safari 2.0.3+ (and probably 1.3.2+): - // works fine, except when changeUrl is used. When changeUrl is used, - // Safari jumps all the way back to whatever page was shown before - // the page that uses dojo.undo.browser support. - // IE 5.5 SP2: - // back button behavior is macro. It does not move back to the - // previous hash value, but to the last full page load. This suggests - // that the iframe is the correct way to capture the back button in - // these cases. - // Don't test this page using local disk for MSIE. MSIE will not create - // a history list for iframe_history.html if served from a file: URL. - // The XML served back from the XHR tests will also not be properly - // created if served from local disk. Serve the test pages from a web - // server to test in that browser. - // IE 6.0: - // same behavior as IE 5.5 SP2 - // Firefox 1.0+: - // the back button will return us to the previous hash on the same - // page, thereby not requiring an iframe hack, although we do then - // need to run a timer to detect inter-page movement. - - //If addToHistory is called, then that means we prune the - //forward stack -- the user went back, then wanted to - //start a new forward path. - forwardStack = []; - - var hash = null; - var url = null; - if(!historyIframe){ - if(dojo.config["useXDomain"] && !dojo.config["dojoIframeHistoryUrl"]){ - console.debug("dojo.back: When using cross-domain Dojo builds," - + " please save iframe_history.html to your domain and set djConfig.dojoIframeHistoryUrl" - + " to the path on your domain to iframe_history.html"); - } - historyIframe = window.frames["dj_history"]; - } - if(!bookmarkAnchor){ - bookmarkAnchor = document.createElement("a"); - dojo.body().appendChild(bookmarkAnchor); - bookmarkAnchor.style.display = "none"; - } - if(args["changeUrl"]){ - hash = ""+ ((args["changeUrl"]!==true) ? args["changeUrl"] : (new Date()).getTime()); - - //If the current hash matches the new one, just replace the history object with - //this new one. It doesn't make sense to track different state objects for the same - //logical URL. This matches the browser behavior of only putting in one history - //item no matter how many times you click on the same #hash link, at least in Firefox - //and Safari, and there is no reliable way in those browsers to know if a #hash link - //has been clicked on multiple times. So making this the standard behavior in all browsers - //so that dojo.back's behavior is the same in all browsers. - if(historyStack.length == 0 && initialState.urlHash == hash){ - initialState = createState(url, args, hash); - return; - }else if(historyStack.length > 0 && historyStack[historyStack.length - 1].urlHash == hash){ - historyStack[historyStack.length - 1] = createState(url, args, hash); - return; - } - - changingUrl = true; - setTimeout(function() { - setHash(hash); - changingUrl = false; - }, 1); - bookmarkAnchor.href = hash; - - if(dojo.isIE){ - url = loadIframeHistory(); - - var oldCB = args["back"]||args["backButton"]||args["handle"]; - - //The function takes handleName as a parameter, in case the - //callback we are overriding was "handle". In that case, - //we will need to pass the handle name to handle. - var tcb = function(handleName){ - if(getHash() != ""){ - setTimeout(function() { setHash(hash); }, 1); - } - //Use apply to set "this" to args, and to try to avoid memory leaks. - oldCB.apply(this, [handleName]); - }; - - //Set interceptor function in the right place. - if(args["back"]){ - args.back = tcb; - }else if(args["backButton"]){ - args.backButton = tcb; - }else if(args["handle"]){ - args.handle = tcb; - } - - var oldFW = args["forward"]||args["forwardButton"]||args["handle"]; - - //The function takes handleName as a parameter, in case the - //callback we are overriding was "handle". In that case, - //we will need to pass the handle name to handle. - var tfw = function(handleName){ - if(getHash() != ""){ - setHash(hash); - } - if(oldFW){ // we might not actually have one - //Use apply to set "this" to args, and to try to avoid memory leaks. - oldFW.apply(this, [handleName]); - } - }; - - //Set interceptor function in the right place. - if(args["forward"]){ - args.forward = tfw; - }else if(args["forwardButton"]){ - args.forwardButton = tfw; - }else if(args["handle"]){ - args.handle = tfw; - } - - }else if(!dojo.isIE){ - // start the timer - if(!locationTimer){ - locationTimer = setInterval(checkLocation, 200); - } - - } - }else{ - url = loadIframeHistory(); - } - - historyStack.push(createState(url, args, hash)); - }; - - back._iframeLoaded = function(evt, ifrLoc){ - //summary: - // private method. Do not call this directly. - var query = getUrlQuery(ifrLoc.href); - if(query == null){ - // alert("iframeLoaded"); - // we hit the end of the history, so we should go back - if(historyStack.length == 1){ - handleBackButton(); - } - return; - } - if(moveForward){ - // we were expecting it, so it's not either a forward or backward movement - moveForward = false; - return; - } - - //Check the back stack first, since it is more likely. - //Note that only one step back or forward is supported. - if(historyStack.length >= 2 && query == getUrlQuery(historyStack[historyStack.length-2].url)){ - handleBackButton(); - }else if(forwardStack.length > 0 && query == getUrlQuery(forwardStack[forwardStack.length-1].url)){ - handleForwardButton(); - } - }; - })(); - +if(!dojo._hasResource["dojo.back"]){ +dojo._hasResource["dojo.back"]=true; +dojo.provide("dojo.back"); +(function(){ +var _1=dojo.back; +function _2(){ +var h=window.location.hash; +if(h.charAt(0)=="#"){ +h=h.substring(1); } +return dojo.isMozilla?h:decodeURIComponent(h); +}; +function _4(h){ +if(!h){ +h=""; +} +window.location.hash=encodeURIComponent(h); +_6=history.length; +}; +if(dojo.exists("tests.back-hash")){ +_1.getHash=_2; +_1.setHash=_4; +} +var _7=(typeof (window)!=="undefined")?window.location.href:""; +var _8=(typeof (window)!=="undefined")?_2():""; +var _9=null; +var _a=null; +var _b=null; +var _c=null; +var _d=[]; +var _e=[]; +var _f=false; +var _10=false; +var _6; +function _11(){ +var _12=_e.pop(); +if(!_12){ +return; +} +var _13=_e[_e.length-1]; +if(!_13&&_e.length==0){ +_13=_9; +} +if(_13){ +if(_13.kwArgs["back"]){ +_13.kwArgs["back"](); +}else{ +if(_13.kwArgs["backButton"]){ +_13.kwArgs["backButton"](); +}else{ +if(_13.kwArgs["handle"]){ +_13.kwArgs.handle("back"); +} +} +} +} +_d.push(_12); +}; +_1.goBack=_11; +function _14(){ +var _15=_d.pop(); +if(!_15){ +return; +} +if(_15.kwArgs["forward"]){ +_15.kwArgs.forward(); +}else{ +if(_15.kwArgs["forwardButton"]){ +_15.kwArgs.forwardButton(); +}else{ +if(_15.kwArgs["handle"]){ +_15.kwArgs.handle("forward"); +} +} +} +_e.push(_15); +}; +_1.goForward=_14; +function _16(url,_18,_19){ +return {"url":url,"kwArgs":_18,"urlHash":_19}; +}; +function _1a(url){ +var _1c=url.split("?"); +if(_1c.length<2){ +return null; +}else{ +return _1c[1]; +} +}; +function _1d(){ +var url=(dojo.config["dojoIframeHistoryUrl"]||dojo.moduleUrl("dojo","resources/iframe_history.html"))+"?"+(new Date()).getTime(); +_f=true; +if(_c){ +dojo.isWebKit?_c.location=url:window.frames[_c.name].location=url; +}else{ +} +return url; +}; +function _1f(){ +if(!_10){ +var hsl=_e.length; +var _21=_2(); +if((_21===_8||window.location.href==_7)&&(hsl==1)){ +_11(); +return; +} +if(_d.length>0){ +if(_d[_d.length-1].urlHash===_21){ +_14(); +return; +} +} +if((hsl>=2)&&(_e[hsl-2])){ +if(_e[hsl-2].urlHash===_21){ +_11(); +return; +} +} +if(dojo.isSafari&&dojo.isSafari<3){ +var _22=history.length; +if(_22>_6){ +_14(); +}else{ +if(_22<_6){ +_11(); +} +} +_6=_22; +} +} +}; +_1.init=function(){ +if(dojo.byId("dj_history")){ +return; +} +var src=dojo.config["dojoIframeHistoryUrl"]||dojo.moduleUrl("dojo","resources/iframe_history.html"); +document.write("<iframe style=\"border:0;width:1px;height:1px;position:absolute;visibility:hidden;bottom:0;right:0;\" name=\"dj_history\" id=\"dj_history\" src=\""+src+"\"></iframe>"); +}; +_1.setInitialState=function(_24){ +_9=_16(_7,_24,_8); +}; +_1.addToHistory=function(_25){ +_d=[]; +var _26=null; +var url=null; +if(!_c){ +if(dojo.config["useXDomain"]&&!dojo.config["dojoIframeHistoryUrl"]){ +console.warn("dojo.back: When using cross-domain Dojo builds,"+" please save iframe_history.html to your domain and set djConfig.dojoIframeHistoryUrl"+" to the path on your domain to iframe_history.html"); +} +_c=window.frames["dj_history"]; +} +if(!_b){ +_b=dojo.create("a",{style:{display:"none"}},dojo.body()); +} +if(_25["changeUrl"]){ +_26=""+((_25["changeUrl"]!==true)?_25["changeUrl"]:(new Date()).getTime()); +if(_e.length==0&&_9.urlHash==_26){ +_9=_16(url,_25,_26); +return; +}else{ +if(_e.length>0&&_e[_e.length-1].urlHash==_26){ +_e[_e.length-1]=_16(url,_25,_26); +return; +} +} +_10=true; +setTimeout(function(){ +_4(_26); +_10=false; +},1); +_b.href=_26; +if(dojo.isIE){ +url=_1d(); +var _28=_25["back"]||_25["backButton"]||_25["handle"]; +var tcb=function(_2a){ +if(_2()!=""){ +setTimeout(function(){ +_4(_26); +},1); +} +_28.apply(this,[_2a]); +}; +if(_25["back"]){ +_25.back=tcb; +}else{ +if(_25["backButton"]){ +_25.backButton=tcb; +}else{ +if(_25["handle"]){ +_25.handle=tcb; +} +} +} +var _2b=_25["forward"]||_25["forwardButton"]||_25["handle"]; +var tfw=function(_2d){ +if(_2()!=""){ +_4(_26); +} +if(_2b){ +_2b.apply(this,[_2d]); +} +}; +if(_25["forward"]){ +_25.forward=tfw; +}else{ +if(_25["forwardButton"]){ +_25.forwardButton=tfw; +}else{ +if(_25["handle"]){ +_25.handle=tfw; +} +} +} +}else{ +if(!dojo.isIE){ +if(!_a){ +_a=setInterval(_1f,200); +} +} +} +}else{ +url=_1d(); +} +_e.push(_16(url,_25,_26)); +}; +_1._iframeLoaded=function(evt,_2f){ +var _30=_1a(_2f.href); +if(_30==null){ +if(_e.length==1){ +_11(); +} +return; +} +if(_f){ +_f=false; +return; +} +if(_e.length>=2&&_30==_1a(_e[_e.length-2].url)){ +_11(); +}else{ +if(_d.length>0&&_30==_1a(_d[_d.length-1].url)){ +_14(); +} +} +}; +})(); +} Deleted: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/dojo.js 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/js/dojo/dojo.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,20 +0,0 @@ -/* - Copyright (c) 2004-2008, The Dojo Foundation - All Rights Reserved. - - Licensed under the Academic Free License version 2.1 or above OR the - modified BSD license. For more information on Dojo licensing, see: - - http://dojotoolkit.org/book/dojo-book-0-9/introduction/licensing -*/ - -/* - This is a compiled version of Dojo, built for deployment and not for - development. To get an editable version, please visit: - - http://dojotoolkit.org - - for documentation and information on getting the source. -*/ - -(function(){var _1=null;if((_1||(typeof djConfig!="undefined"&&djConfig.scopeMap))&&(typeof window!="undefined")){var _2="",_3="",_4="",_5={},_6={};_1=_1||djConfig.scopeMap;for(var i=0;i<_1.length;i++){var _8=_1[i];_2+="var "+_8[0]+" = {}; "+_8[1]+" = "+_8[0]+";"+_8[1]+"._scopeName = '"+_8[1]+"';";_3+=(i==0?"":",")+_8[0];_4+=(i==0?"":",")+_8[1];_5[_8[0]]=_8[1];_6[_8[1]]=_8[0];}eval(_2+"dojo._scopeArgs = ["+_4+"];");dojo._scopePrefixArgs=_3;dojo._scopePrefix="(function("+_3+"){";dojo._scopeSuffix="})("+_4+")";dojo._scopeMap=_5;dojo._scopeMapRev=_6;}(function(){if(!this["console"]){this.console={log:function(){}};}var cn=["assert","count","debug","dir","dirxml","error","group","groupEnd","info","profile","profileEnd","time","timeEnd","trace","warn","log"];var i=0,tn;while((tn=cn[i++])){if(!console[tn]){(function(){var _c=tn+"";console[_c]=function(){var a=Array.apply({},arguments);a.unshift(_c+":");console.log(a.join(" "));};})();}}if(typeof dojo=="undefined"){this.dojo={_scopeName:"dojo",_scopePrefix:"",_scopePrefixArgs:"",_scopeSuffix:"",_scopeMap:{},_scopeMapRev:{}};}var d=dojo;if(typeof dijit=="undefined"){this.dijit={_scopeName:"dijit"};}if(typeof dojox=="undefined"){this.dojox={_scopeName:"dojox"};}if(!d._scopeArgs){d._scopeArgs=[dojo,dijit,dojox];}d.global=this;d.config={isDebug:false,debugAtAllCosts:false};if(typeof djConfig!="undefined"){for(var _f in djConfig){d.config[_f]=djConfig[_f];}}var _10=["Browser","Rhino","Spidermonkey","Mobile"];var t;while((t=_10.shift())){d["is"+t]=false;}dojo.locale=d.config.locale;var rev="$Rev: 13707 $".match(/\d+/);dojo.version={major:1,minor:1,patch:1,flag:"",revision:rev?+rev[0]:999999,toString:function(){with(d.version){return major+"."+minor+"."+patch+flag+" ("+revision+")";}}};if(typeof OpenAjax!="undefined"){OpenAjax.hub.registerLibrary(dojo._scopeName,"http://dojotoolkit.org",d.version.toString());}dojo._mixin=function(obj,_14){var _15={};for(var x in _14){if(_15[x]===undefined||_15[x]!=_14[x]){obj[x]=_14[x];}}if(d["isIE"]&&_14){var p=_14.toString;if(typeof p=="function"&&p!=obj.toString&&p!=_15.toString&&p!="\nfunction toString() {\n [native code]\n}\n"){obj.toString=_14.toString;}}return obj;};dojo.mixin=function(obj,_19){for(var i=1,l=arguments.length;i<l;i++){d._mixin(obj,arguments[i]);}return obj;};dojo._getProp=function(_1c,_1d,_1e){var obj=_1e||d.global;for(var i=0,p;obj&&(p=_1c[i]);i++){if(i==0&&this._scopeMap[p]){p=this._scopeMap[p];}obj=(p in obj?obj[p]:(_1d?obj[p]={}:undefined));}return obj;};dojo.setObject=function(_22,_23,_24){var _25=_22.split("."),p=_25.pop(),obj=d._getProp(_25,true,_24);return obj&&p?(obj[p]=_23):undefined;};dojo.getObject=function(_28,_29,_2a){return d._getProp(_28.split("."),_29,_2a);};dojo.exists=function(_2b,obj){return !!d.getObject(_2b,false,obj);};dojo["eval"]=function(_2d){return d.global.eval?d.global.eval(_2d):eval(_2d);};d.deprecated=d.experimental=function(){};})();(function(){var d=dojo;d.mixin(d,{_loadedModules:{},_inFlightCount:0,_hasResource:{},_modulePrefixes:{dojo:{name:"dojo",value:"."},doh:{name:"doh",value:"../util/doh"},tests:{name:"tests",value:"tests"}},_moduleHasPrefix:function(_2f){var mp=this._modulePrefixes;return !!(mp[_2f]&&mp[_2f].value);},_getModulePrefix:function(_31){var mp=this._modulePrefixes;if(this._moduleHasPrefix(_31)){return mp[_31].value;}return _31;},_loadedUrls:[],_postLoad:false,_loaders:[],_unloaders:[],_loadNotifying:false});dojo._loadPath=function(_33,_34,cb){var uri=((_33.charAt(0)=="/"||_33.match(/^\w+:/))?"":this.baseUrl)+_33;try{return !_34?this._loadUri(uri,cb):this._loadUriAndCheck(uri,_34,cb);}catch(e){console.error(e);return false;}};dojo._loadUri=function(uri,cb){if(this._loadedUrls[uri]){return true;}var _39=this._getText(uri,true);if(!_39){return false;}this._loadedUrls[uri]=true;this._loadedUrls.push(uri);if(cb){_39="("+_39+")";}else{_39=this._scopePrefix+_39+this._scopeSuffix;}if(d.isMoz){_39+="\r\n//@ sourceURL="+uri;}var _3a=d["eval"](_39);if(cb){cb(_3a);}return true;};dojo._loadUriAndCheck=function(uri,_3c,cb){var ok=false;try{ok=this._loadUri(uri,cb);}catch(e){console.error("failed loading "+uri+" with error: "+e);}return !!(ok&&this._loadedModules[_3c]);};dojo.loaded=function(){this._loadNotifying=true;this._postLoad=true;var mll=d._loaders;this._loaders=[];for(var x=0;x<mll.length;x++){try{mll[x]();}catch(e){throw e;console.error("dojo.addOnLoad callback failed: "+e,e);}}this._loadNotifying=false;if(d._postLoad&&d._inFlightCount==0&&mll.length){d._callLoaded();}};dojo.unloaded=function(){var mll=this._unloaders;while(mll.length){(mll.pop())();}};var _42=function(arr,obj,fn){if(!fn){arr.push(obj);}else{if(fn){var _46=(typeof fn=="string")?obj[fn]:fn;arr.push(function(){_46.call(obj);});}}};dojo.addOnLoad=function(obj,_48){_42(d._loaders,obj,_48);if(d._postLoad&&d._inFlightCount==0&&!d._loadNotifying){d._callLoaded();}};dojo.addOnUnload=function(obj,_4a){_42(d._unloaders,obj,_4a);};dojo._modulesLoaded=function(){if(d._postLoad){return;}if(d._inFlightCount>0){console.warn("files still in flight!");return;}d._callLoaded();};dojo._callLoaded=function(){if(typeof setTimeout=="object"||(dojo.config.useXDomain&&d.isOpera)){if(dojo.isAIR){setTimeout(function(){dojo.loaded();},0);}else{setTimeout(dojo._scopeName+".loaded();",0);}}else{d.loaded();}};dojo._getModuleSymbols=function(_4b){var _4c=_4b.split(".");for(var i=_4c.length;i>0;i--){var _4e=_4c.slice(0,i).join(".");if((i==1)&&!this._moduleHasPrefix(_4e)){_4c[0]="../"+_4c[0];}else{var _4f=this._getModulePrefix(_4e);if(_4f!=_4e){_4c.splice(0,i,_4f);break;}}}return _4c;};dojo._global_omit_module_check=false;dojo._loadModule=dojo.require=function(_50,_51){_51=this._global_omit_module_check||_51;var _52=this._loadedModules[_50];if(_52){return _52;}var _53=this._getModuleSymbols(_50).join("/")+".js";var _54=(!_51)?_50:null;var ok=this._loadPath(_53,_54);if(!ok&&!_51){throw new Error("Could not load '"+_50+"'; last tried '"+_53+"'");}if(!_51&&!this._isXDomain){_52=this._loadedModules[_50];if(!_52){throw new Error("symbol '"+_50+"' is not defined after loading '"+_53+"'");}}return _52;};dojo.provide=function(_56){_56=_56+"";return (d._loadedModules[_56]=d.getObject(_56,true));};dojo.platformRequire=function(_57){var _58=_57.common||[];var _59=_58.concat(_57[d._name]||_57["default"]||[]);for(var x=0;x<_59.length;x++){var _5b=_59[x];if(_5b.constructor==Array){d._loadModule.apply(d,_5b);}else{d._loadModule(_5b);}}};dojo.requireIf=function(_5c,_5d){if(_5c===true){var _5e=[];for(var i=1;i<arguments.length;i++){_5e.push(arguments[i]);}d.require.apply(d,_5e);}};dojo.requireAfterIf=d.requireIf;dojo.registerModulePath=function(_60,_61){d._modulePrefixes[_60]={name:_60,value:_61};};dojo.requireLocalization=function(_62,_63,_64,_65){d.require("dojo.i18n");d.i18n._requireLocalization.apply(d.hostenv,arguments);};var ore=new RegExp("^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$");var ire=new RegExp("^((([^:]+:)?([^@]+))@)?([^:]*)(:([0-9]+))?$");dojo._Url=function(){var n=null;var _a=arguments;var uri=[_a[0]];for(var i=1;i<_a.length;i++){if(!_a[i]){continue;}var _6c=new d._Url(_a[i]+"");var _6d=new d._Url(uri[0]+"");if(_6c.path==""&&!_6c.scheme&&!_6c.authority&&!_6c.query){if(_6c.fragment!=n){_6d.fragment=_6c.fragment;}_6c=_6d;}else{if(!_6c.scheme){_6c.scheme=_6d.scheme;if(!_6c.authority){_6c.authority=_6d.authority;if(_6c.path.charAt(0)!="/"){var _6e=_6d.path.substring(0,_6d.path.lastIndexOf("/")+1)+_6c.path;var _6f=_6e.split("/");for(var j=0;j<_6f.length;j++){if(_6f[j]=="."){if(j==_6f.length-1){_6f[j]="";}else{_6f.splice(j,1);j--;}}else{if(j>0&&!(j==1&&_6f[0]=="")&&_6f[j]==".."&&_6f[j-1]!=".."){if(j==(_6f.length-1)){_6f.splice(j,1);_6f[j-1]="";}else{_6f.splice(j-1,2);j-=2;}}}}_6c.path=_6f.join("/");}}}}uri=[];if(_6c.scheme){uri.push(_6c.scheme,":");}if(_6c.authority){uri.push("//",_6c.authority);}uri.push(_6c.path);if(_6c.query){uri.push("?",_6c.query);}if(_6c.fragment){uri.push("#",_6c.fragment);}}this.uri=uri.join("");var r=this.uri.match(ore);this.scheme=r[2]||(r[1]?"":n);this.authority=r[4]||(r[3]?"":n);this.path=r[5];this.query=r[7]||(r[6]?"":n);this.fragment=r[9]||(r[8]?"":n);if(this.authority!=n){r=this.authority.match(ire);this.user=r[3]||n;this.password=r[4]||n;this.host=r[5];this.port=r[7]||n;}};dojo._Url.prototype.toString=function(){return this.uri;};dojo.moduleUrl=function(_72,url){var loc=d._getModuleSymbols(_72).join("/");if(!loc){return null;}if(loc.lastIndexOf("/")!=loc.length-1){loc+="/";}var _75=loc.indexOf(":");if(loc.charAt(0)!="/"&&(_75==-1||_75>loc.indexOf("/"))){loc=d.baseUrl+loc;}return new d._Url(loc,url);};})();if(typeof window!="undefined"){dojo.isBrowser=true;dojo._name="browser";(function(){var d=dojo;if(document&&document.getElementsByTagName){var _77=document.getElementsByTagName("script");var _78=/dojo(\.xd)?\.js(\W|$)/i;for(var i=0;i<_77.length;i++){var src=_77[i].getAttribute("src");if(!src){continue;}var m=src.match(_78);if(m){if(!d.config.baseUrl){d.config.baseUrl=src.substring(0,m.index);}var cfg=_77[i].getAttribute("djConfig");if(cfg){var _7d=eval("({ "+cfg+" })");for(var x in _7d){dojo.config[x]=_7d[x];}}break;}}}d.baseUrl=d.config.baseUrl;var n=navigator;var dua=n.userAgent;var dav=n.appVersion;var tv=parseFloat(dav);d.isOpera=(dua.indexOf("Opera")>=0)?tv:0;var idx=Math.max(dav.indexOf("WebKit"),dav.indexOf("Safari"),0);if(idx){d.isSafari=parseFloat(dav.split("Version/")[1])||((parseFloat(dav.substr(idx+7))>=419.3)?3:2)||2;}d.isAIR=(dua.indexOf("AdobeAIR")>=0)?1:0;d.isKhtml=(dav.indexOf("Konqueror")>=0||d.isSafari)?tv:0;d.isMozilla=d.isMoz=(dua.indexOf("Gecko")>=0&&!d.isKhtml)?tv:0;d.isFF=d.isIE=0;if(d.isMoz){d.isFF=parseFloat(dua.split("Firefox/")[1])||0;}if(document.all&&!d.isOpera){d.isIE=parseFloat(dav.split("MSIE ")[1])||0;}if(dojo.isIE&&window.location.protocol==="file:"){dojo.config.ieForceActiveXXhr=true;}var cm=document.compatMode;d.isQuirks=cm=="BackCompat"||cm=="QuirksMode"||d.isIE<6;d.locale=dojo.config.locale||(d.isIE?n.userLanguage:n.language).toLowerCase();d._XMLHTTP_PROGIDS=["Msxml2.XMLHTTP","Microsoft.XMLHTTP","Msxml2.XMLHTTP.4.0"];d._xhrObj=function(){var _85=null;var _86=null;if(!dojo.isIE||!dojo.config.ieForceActiveXXhr){try{_85=new XMLHttpRequest();}catch(e){}}if(!_85){for(var i=0;i<3;++i){var _88=d._XMLHTTP_PROGIDS[i];try{_85=new ActiveXObject(_88);}catch(e){_86=e;}if(_85){d._XMLHTTP_PROGIDS=[_88];break;}}}if(!_85){throw new Error("XMLHTTP not available: "+_86);}return _85;};d._isDocumentOk=function(_89){var _8a=_89.status||0;return (_8a>=200&&_8a<300)||_8a==304||_8a==1223||(!_8a&&(location.protocol=="file:"||location.protocol=="chrome:"));};var _8b=window.location+"";var _8c=document.getElementsByTagName("base");var _8d=(_8c&&_8c.length>0);d._getText=function(uri,_8f){var _90=this._xhrObj();if(!_8d&&dojo._Url){uri=(new dojo._Url(_8b,uri)).toString();}if(d.config.cacheBust){uri+=(uri.indexOf("?")==-1?"?":"&")+String(d.config.cacheBust).replace(/\W+/g,"");}_90.open("GET",uri,false);try{_90.send(null);if(!d._isDocumentOk(_90)){var err=Error("Unable to load "+uri+" status:"+_90.status);err.status=_90.status;err.responseText=_90.responseText;throw err;}}catch(e){if(_8f){return null;}throw e;}return _90.responseText;};})();dojo._initFired=false;dojo._loadInit=function(e){dojo._initFired=true;var _93=(e&&e.type)?e.type.toLowerCase():"load";if(arguments.callee.initialized||(_93!="domcontentloaded"&&_93!="load")){return;}arguments.callee.initialized=true;if("_khtmlTimer" in dojo){clearInterval(dojo._khtmlTimer);delete dojo._khtmlTimer;}if(dojo._inFlightCount==0){dojo._modulesLoaded();}};dojo._fakeLoadInit=function(){dojo._loadInit({type:"load"});};if(!dojo.config.afterOnLoad){if(document.addEventListener){if(dojo.isOpera||dojo.isFF>=3||(dojo.isMoz&&dojo.config.enableMozDomContentLoaded===true)){document.addEventListener("DOMContentLoaded",dojo._loadInit,null);}window.addEventListener("load",dojo._loadInit,null);}if(dojo.isAIR){window.addEventListener("load",dojo._loadInit,null);}else{if(/(WebKit|khtml)/i.test(navigator.userAgent)){dojo._khtmlTimer=setInterval(function(){if(/loaded|complete/.test(document.readyState)){dojo._loadInit();}},10);}}}(function(){var _w=window;var _95=function(_96,fp){var _98=_w[_96]||function(){};_w[_96]=function(){fp.apply(_w,arguments);_98.apply(_w,arguments);};};if(dojo.isIE){if(!dojo.config.afterOnLoad){document.write("<scr"+"ipt defer src=\"//:\" "+"onreadystatechange=\"if(this.readyState=='complete'){"+dojo._scopeName+"._loadInit();}\">"+"</scr"+"ipt>");}var _99=true;_95("onbeforeunload",function(){_w.setTimeout(function(){_99=false;},0);});_95("onunload",function(){if(_99){dojo.unloaded();}});try{document.namespaces.add("v","urn:schemas-microsoft-com:vml");document.createStyleSheet().addRule("v\\:*","behavior:url(#default#VML)");}catch(e){}}else{_95("onbeforeunload",function(){dojo.unloaded();});}})();}(function(){var mp=dojo.config["modulePaths"];if(mp){for(var _9b in mp){dojo.registerModulePath(_9b,mp[_9b]);}}})();if(dojo.config.isDebug){dojo.require("dojo._firebug.firebug");}if(dojo.config.debugAtAllCosts){dojo.config.useXDomain=true;dojo.require("dojo._base._loader.loader_xd");dojo.require("dojo._base._loader.loader_debug");dojo.require("dojo.i18n");}if(!dojo._hasResource["dojo._base.lang"]){dojo._hasResource["dojo._base.lang"]=true;dojo.provide("dojo._base.lang");dojo.isString=function(it){return !!arguments.length&&it!=null&&(typeof it=="string"||it instanceof String);};dojo.isArray=function(it){return it&&(it instanceof Array||typeof it=="array");};dojo.isFunction=(function(){var _9e=function(it){return it&&(typeof it=="function"||it instanceof Function);};return dojo.isSafari?function(it){if(typeof it=="function"&&it=="[object NodeList]"){return false;}return _9e(it);}:_9e;})();dojo.isObject=function(it){return it!==undefined&&(it===null||typeof it=="object"||dojo.isArray(it)||dojo.isFunction(it));};dojo.isArrayLike=function(it){var d=dojo;return it&&it!==undefined&&!d.isString(it)&&!d.isFunction(it)&&!(it.tagName&&it.tagName.toLowerCase()=="form")&&(d.isArray(it)||isFinite(it.length));};dojo.isAlien=function(it){return it&&!dojo.isFunction(it)&&/\{\s*\[native code\]\s*\}/.test(String(it));};dojo.extend=function(_a5,_a6){for(var i=1,l=arguments.length;i<l;i++){dojo._mixin(_a5.prototype,arguments[i]);}return _a5;};dojo._hitchArgs=function(_a9,_aa){var pre=dojo._toArray(arguments,2);var _ac=dojo.isString(_aa);return function(){var _ad=dojo._toArray(arguments);var f=_ac?(_a9||dojo.global)[_aa]:_aa;return f&&f.apply(_a9||this,pre.concat(_ad));};};dojo.hitch=function(_af,_b0){if(arguments.length>2){return dojo._hitchArgs.apply(dojo,arguments);}if(!_b0){_b0=_af;_af=null;}if(dojo.isString(_b0)){_af=_af||dojo.global;if(!_af[_b0]){throw (["dojo.hitch: scope[\"",_b0,"\"] is null (scope=\"",_af,"\")"].join(""));}return function(){return _af[_b0].apply(_af,arguments||[]);};}return !_af?_b0:function(){return _b0.apply(_af,arguments||[]);};};dojo.delegate=dojo._delegate=function(obj,_b2){function TMP(){};TMP.prototype=obj;var tmp=new TMP();if(_b2){dojo.mixin(tmp,_b2);}return tmp;};dojo.partial=function(_b4){var arr=[null];return dojo.hitch.apply(dojo,arr.concat(dojo._toArray(arguments)));};dojo._toArray=function(obj,_b7,_b8){var arr=_b8||[];for(var x=_b7||0;x<obj.length;x++){arr.push(obj[x]);}return arr;};dojo.clone=function(o){if(!o){return o;}if(dojo.isArray(o)){var r=[];for(var i=0;i<o.length;++i){r.push(dojo.clone(o[i]));}return r;}if(!dojo.isObject(o)){return o;}if(o.nodeType&&o.cloneNode){return o.cloneNode(true);}if(o instanceof Date){return new Date(o.getTime());}var r=new o.constructor();for(var i in o){if(!(i in r)||r[i]!=o[i]){r[i]=dojo.clone(o[i]);}}return r;};dojo.trim=function(str){return str.replace(/^\s\s*/,"").replace(/\s\s*$/,"");};}if(!dojo._hasResource["dojo._base.declare"]){dojo._hasResource["dojo._base.declare"]=true;dojo.provide("dojo._base.declare");dojo.declare=function(_bf,_c0,_c1){var dd=arguments.callee,_c3;if(dojo.isArray(_c0)){_c3=_c0;_c0=_c3.shift();}if(_c3){dojo.forEach(_c3,function(m){if(!m){throw (_bf+": mixin #"+i+" is null");}_c0=dd._delegate(_c0,m);});}var _c5=(_c1||0).constructor,_c6=dd._delegate(_c0),fn;for(var i in _c1){if(dojo.isFunction(fn=_c1[i])&&!0[i]){fn.nom=i;}}dojo.extend(_c6,{declaredClass:_bf,_constructor:_c5,preamble:null},_c1||0);_c6.prototype.constructor=_c6;return dojo.setObject(_bf,_c6);};dojo.mixin(dojo.declare,{_delegate:function(_c9,_ca){var bp=(_c9||0).prototype,mp=(_ca||0).prototype;var _cd=dojo.declare._makeCtor();dojo.mixin(_cd,{superclass:bp,mixin:mp,extend:dojo.declare._extend});if(_c9){_cd.prototype=dojo._delegate(bp);}dojo.extend(_cd,dojo.declare._core,mp||0,{_constructor:null,preamble:null});_cd.prototype.constructor=_cd;_cd.prototype.declaredClass=(bp||0).declaredClass+"_"+(mp||0).declaredClass;return _cd;},_extend:function(_ce){for(var i in _ce){if(dojo.isFunction(fn=_ce[i])&&!0[i]){fn.nom=i;}}dojo.extend(this,_ce);},_makeCtor:function(){return function(){this._construct(arguments);};},_core:{_construct:function(_d0){var c=_d0.callee,s=c.superclass,ct=s&&s.constructor,m=c.mixin,mct=m&&m.constructor,a=_d0,ii,fn;if(a[0]){if(((fn=a[0].preamble))){a=fn.apply(this,a)||a;}}if((fn=c.prototype.preamble)){a=fn.apply(this,a)||a;}if(ct&&ct.apply){ct.apply(this,a);}if(mct&&mct.apply){mct.apply(this,a);}if((ii=c.prototype._constructor)){ii.apply(this,_d0);}if(this.constructor.prototype==c.prototype&&(ct=this.postscript)){ct.apply(this,_d0);}},_findMixin:function(_d9){var c=this.constructor,p,m;while(c){p=c.superclass;m=c.mixin;if(m==_d9||(m instanceof _d9.constructor)){return p;}if(m&&(m=m._findMixin(_d9))){return m;}c=p&&p.constructor;}},_findMethod:function(_dd,_de,_df,has){var p=_df,c,m,f;do{c=p.constructor;m=c.mixin;if(m&&(m=this._findMethod(_dd,_de,m,has))){return m;}if((f=p[_dd])&&(has==(f==_de))){return p;}p=c.superclass;}while(p);return !has&&(p=this._findMixin(_df))&&this._findMethod(_dd,_de,p,has);},inherited:function(_e5,_e6,_e7){var a=arguments;if(!dojo.isString(a[0])){_e7=_e6;_e6=_e5;_e5=_e6.callee.nom;}a=_e7||_e6;var c=_e6.callee,p=this.constructor.prototype,fn,mp;if(this[_e5]!=c||p[_e5]==c){mp=this._findMethod(_e5,c,p,true);if(!mp){throw (this.declaredClass+": inherited method \""+_e5+"\" mismatch");}p=this._findMethod(_e5,c,mp,false);}fn=p&&p[_e5];if(!fn){throw (mp.declaredClass+": inherited method \""+_e5+"\" not found");}return fn.apply(this,a);}}});}if(!dojo._hasResource["dojo._base.connect"]){dojo._hasResource["dojo._base.connect"]=true;dojo.provide("dojo._base.connect");dojo._listener={getDispatcher:function(){return function(){var ap=Array.prototype,c=arguments.callee,ls=c._listeners,t=c.target;var r=t&&t.apply(this,arguments);for(var i in ls){if(!(i in ap)){ls[i].apply(this,arguments);}}return r;};},add:function(_f3,_f4,_f5){_f3=_f3||dojo.global;var f=_f3[_f4];if(!f||!f._listeners){var d=dojo._listener.getDispatcher();d.target=f;d._listeners=[];f=_f3[_f4]=d;}return f._listeners.push(_f5);},remove:function(_f8,_f9,_fa){var f=(_f8||dojo.global)[_f9];if(f&&f._listeners&&_fa--){delete f._listeners[_fa];}}};dojo.connect=function(obj,_fd,_fe,_ff,_100){var a=arguments,args=[],i=0;args.push(dojo.isString(a[0])?null:a[i++],a[i++]);var a1=a[i+1];args.push(dojo.isString(a1)||dojo.isFunction(a1)?a[i++]:null,a[i++]);for(var l=a.length;i<l;i++){args.push(a[i]);}return dojo._connect.apply(this,args);};dojo._connect=function(obj,_106,_107,_108){var l=dojo._listener,h=l.add(obj,_106,dojo.hitch(_107,_108));return [obj,_106,h,l];};dojo.disconnect=function(_10b){if(_10b&&_10b[0]!==undefined){dojo._disconnect.apply(this,_10b);delete _10b[0];}};dojo._disconnect=function(obj,_10d,_10e,_10f){_10f.remove(obj,_10d,_10e);};dojo._topics={};dojo.subscribe=function(_110,_111,_112){return [_110,dojo._listener.add(dojo._topics,_110,dojo.hitch(_111,_112))];};dojo.unsubscribe=function(_113){if(_113){dojo._listener.remove(dojo._topics,_113[0],_113[1]);}};dojo.publish=function(_114,args){var f=dojo._topics[_114];if(f){f.apply(this,args||[]);}};dojo.connectPublisher=function(_117,obj,_119){var pf=function(){dojo.publish(_117,arguments);};return (_119)?dojo.connect(obj,_119,pf):dojo.connect(obj,pf);};}if(!dojo._hasResource["dojo._base.Deferred"]){dojo._hasResource["dojo._base.Deferred"]=true;dojo.provide("dojo._base.Deferred");dojo.Deferred=function(_11b){this.chain=[];this.id=this._nextId();this.fired=-1;this.paused=0;this.results=[null,null];this.canceller=_11b;this.silentlyCancelled=false;};dojo.extend(dojo.Deferred,{_nextId:(function(){var n=1;return function(){return n++;};})(),cancel:function(){var err;if(this.fired==-1){if(this.canceller){err=this.canceller(this);}else{this.silentlyCancelled=true;}if(this.fired==-1){if(!(err instanceof Error)){var res=err;err=new Error("Deferred Cancelled");err.dojoType="cancel";err.cancelResult=res;}this.errback(err);}}else{if((this.fired==0)&&(this.results[0] instanceof dojo.Deferred)){this.results[0].cancel();}}},_resback:function(res){this.fired=((res instanceof Error)?1:0);this.results[this.fired]=res;this._fire();},_check:function(){if(this.fired!=-1){if(!this.silentlyCancelled){throw new Error("already called!");}this.silentlyCancelled=false;return;}},callback:function(res){this._check();this._resback(res);},errback:function(res){this._check();if(!(res instanceof Error)){res=new Error(res);}this._resback(res);},addBoth:function(cb,cbfn){var _124=dojo.hitch.apply(dojo,arguments);return this.addCallbacks(_124,_124);},addCallback:function(cb,cbfn){return this.addCallbacks(dojo.hitch.apply(dojo,arguments));},addErrback:function(cb,cbfn){return this.addCallbacks(null,dojo.hitch.apply(dojo,arguments));},addCallbacks:function(cb,eb){this.chain.push([cb,eb]);if(this.fired>=0){this._fire();}return this;},_fire:function(){var _12b=this.chain;var _12c=this.fired;var res=this.results[_12c];var self=this;var cb=null;while((_12b.length>0)&&(this.paused==0)){var f=_12b.shift()[_12c];if(!f){continue;}try{res=f(res);_12c=((res instanceof Error)?1:0);if(res instanceof dojo.Deferred){cb=function(res){self._resback(res);self.paused--;if((self.paused==0)&&(self.fired>=0)){self._fire();}};this.paused++;}}catch(err){console.debug(err);_12c=1;res=err;}}this.fired=_12c;this.results[_12c]=res;if((cb)&&(this.paused)){res.addBoth(cb);}}});}if(!dojo._hasResource["dojo._base.json"]){dojo._hasResource["dojo._base.json"]=true;dojo.provide("dojo._base.json");dojo.fromJson=function(json){return eval("("+json+")");};dojo._escapeString=function(str){return ("\""+str.replace(/(["\\])/g,"\\$1")+"\"").replace(/[\f]/g,"\\f").replace(/[\b]/g,"\\b").replace(/[\n]/g,"\\n").replace(/[\t]/g,"\\t").replace(/[\r]/g,"\\r");};dojo.toJsonIndentStr="\t";dojo.toJson=function(it,_135,_136){if(it===undefined){return "undefined";}var _137=typeof it;if(_137=="number"||_137=="boolean"){return it+"";}if(it===null){return "null";}if(dojo.isString(it)){return dojo._escapeString(it);}if(it.nodeType&&it.cloneNode){return "";}var _138=arguments.callee;var _139;_136=_136||"";var _13a=_135?_136+dojo.toJsonIndentStr:"";if(typeof it.__json__=="function"){_139=it.__json__();if(it!==_139){return _138(_139,_135,_13a);}}if(typeof it.json=="function"){_139=it.json();if(it!==_139){return _138(_139,_135,_13a);}}var sep=_135?" ":"";var _13c=_135?"\n":"";if(dojo.isArray(it)){var res=dojo.map(it,function(obj){var val=_138(obj,_135,_13a);if(typeof val!="string"){val="undefined";}return _13c+_13a+val;});return "["+res.join(","+sep)+_13c+_136+"]";}if(_137=="function"){return null;}var _140=[];for(var key in it){var _142;if(typeof key=="number"){_142="\""+key+"\"";}else{if(typeof key=="string"){_142=dojo._escapeString(key);}else{continue;}}val=_138(it[key],_135,_13a);if(typeof val!="string"){continue;}_140.push(_13c+_13a+_142+":"+sep+val);}return "{"+_140.join(","+sep)+_13c+_136+"}";};}if(!dojo._hasResource["dojo._base.array"]){dojo._hasResource["dojo._base.array"]=true;dojo.provide("dojo._base.array");(function(){var _143=function(arr,obj,cb){return [dojo.isString(arr)?arr.split(""):arr,obj||dojo.global,dojo.isString(cb)?new Function("item","index","array",cb):cb];};dojo.mixin(dojo,{indexOf:function(_147,_148,_149,_14a){var step=1,end=_147.length||0,i=0;if(_14a){i=end-1;step=end=-1;}if(_149!=undefined){i=_149;}if((_14a&&i>end)||i<end){for(;i!=end;i+=step){if(_147[i]==_148){return i;}}}return -1;},lastIndexOf:function(_14d,_14e,_14f){return dojo.indexOf(_14d,_14e,_14f,true);},forEach:function(arr,_151,_152){if(!arr||!arr.length){return;}var _p=_143(arr,_152,_151);arr=_p[0];for(var i=0,l=_p[0].length;i<l;i++){_p[2].call(_p[1],arr[i],i,arr);}},_everyOrSome:function(_156,arr,_158,_159){var _p=_143(arr,_159,_158);arr=_p[0];for(var i=0,l=arr.length;i<l;i++){var _15d=!!_p[2].call(_p[1],arr[i],i,arr);if(_156^_15d){return _15d;}}return _156;},every:function(arr,_15f,_160){return this._everyOrSome(true,arr,_15f,_160);},some:function(arr,_162,_163){return this._everyOrSome(false,arr,_162,_163);},map:function(arr,_165,_166){var _p=_143(arr,_166,_165);arr=_p[0];var _168=(arguments[3]?(new arguments[3]()):[]);for(var i=0;i<arr.length;++i){_168.push(_p[2].call(_p[1],arr[i],i,arr));}return _168;},filter:function(arr,_16b,_16c){var _p=_143(arr,_16c,_16b);arr=_p[0];var _16e=[];for(var i=0;i<arr.length;i++){if(_p[2].call(_p[1],arr[i],i,arr)){_16e.push(arr[i]);}}return _16e;}});})();}if(!dojo._hasResource["dojo._base.Color"]){dojo._hasResource["dojo._base.Color"]=true;dojo.provide("dojo._base.Color");dojo.Color=function(_170){if(_170){this.setColor(_170);}};dojo.Color.named={black:[0,0,0],silver:[192,192,192],gray:[128,128,128],white:[255,255,255],maroon:[128,0,0],red:[255,0,0],purple:[128,0,128],fuchsia:[255,0,255],green:[0,128,0],lime:[0,255,0],olive:[128,128,0],yellow:[255,255,0],navy:[0,0,128],blue:[0,0,255],teal:[0,128,128],aqua:[0,255,255]};dojo.extend(dojo.Color,{r:255,g:255,b:255,a:1,_set:function(r,g,b,a){var t=this;t.r=r;t.g=g;t.b=b;t.a=a;},setColor:function(_176){var d=dojo;if(d.isString(_176)){d.colorFromString(_176,this);}else{if(d.isArray(_176)){d.colorFromArray(_176,this);}else{this._set(_176.r,_176.g,_176.b,_176.a);if(!(_176 instanceof d.Color)){this.sanitize();}}}return this;},sanitize:function(){return this;},toRgb:function(){var t=this;return [t.r,t.g,t.b];},toRgba:function(){var t=this;return [t.r,t.g,t.b,t.a];},toHex:function(){var arr=dojo.map(["r","g","b"],function(x){var s=this[x].toString(16);return s.length<2?"0"+s:s;},this);return "#"+arr.join("");},toCss:function(_17d){var t=this,rgb=t.r+", "+t.g+", "+t.b;return (_17d?"rgba("+rgb+", "+t.a:"rgb("+rgb)+")";},toString:function(){return this.toCss(true);}});dojo.blendColors=function(_180,end,_182,obj){var d=dojo,t=obj||new dojo.Color();d.forEach(["r","g","b","a"],function(x){t[x]=_180[x]+(end[x]-_180[x])*_182;if(x!="a"){t[x]=Math.round(t[x]);}});return t.sanitize();};dojo.colorFromRgb=function(_187,obj){var m=_187.toLowerCase().match(/^rgba?\(([\s\.,0-9]+)\)/);return m&&dojo.colorFromArray(m[1].split(/\s*,\s*/),obj);};dojo.colorFromHex=function(_18a,obj){var d=dojo,t=obj||new d.Color(),bits=(_18a.length==4)?4:8,mask=(1<<bits)-1;_18a=Number("0x"+_18a.substr(1));if(isNaN(_18a)){return null;}d.forEach(["b","g","r"],function(x){var c=_18a&mask;_18a>>=bits;t[x]=bits==4?17*c:c;});t.a=1;return t;};dojo.colorFromArray=function(a,obj){var t=obj||new dojo.Color();t._set(Number(a[0]),Number(a[1]),Number(a[2]),Number(a[3]));if(isNaN(t.a)){t.a=1;}return t.sanitize();};dojo.colorFromString=function(str,obj){var a=dojo.Color.named[str];return a&&dojo.colorFromArray(a,obj)||dojo.colorFromRgb(str,obj)||dojo.colorFromHex(str,obj);};}if(!dojo._hasResource["dojo._base"]){dojo._hasResource["dojo._base"]=true;dojo.provide("dojo._base");}if(!dojo._hasResource["dojo._base.window"]){dojo._hasResource["dojo._base.window"]=true;dojo.provide("dojo._base.window");dojo._gearsObject=function(){var _198;var _199;var _19a=dojo.getObject("google.gears");if(_19a){return _19a;}if(typeof GearsFactory!="undefined"){_198=new GearsFactory();}else{if(dojo.isIE){try{_198=new ActiveXObject("Gears.Factory");}catch(e){}}else{if(navigator.mimeTypes["application/x-googlegears"]){_198=document.createElement("object");_198.setAttribute("type","application/x-googlegears");_198.setAttribute("width",0);_198.setAttribute("height",0);_198.style.display="none";document.documentElement.appendChild(_198);}}}if(!_198){return null;}dojo.setObject("google.gears.factory",_198);return dojo.getObject("google.gears");};dojo.isGears=(!!dojo._gearsObject())||0;dojo.doc=window["document"]||null;dojo.body=function(){return dojo.doc.body||dojo.doc.getElementsByTagName("body")[0];};dojo.setContext=function(_19b,_19c){dojo.global=_19b;dojo.doc=_19c;};dojo._fireCallback=function(_19d,_19e,_19f){if(_19e&&dojo.isString(_19d)){_19d=_19e[_19d];}return _19d.apply(_19e,_19f||[]);};dojo.withGlobal=function(_1a0,_1a1,_1a2,_1a3){var rval;var _1a5=dojo.global;var _1a6=dojo.doc;try{dojo.setContext(_1a0,_1a0.document);rval=dojo._fireCallback(_1a1,_1a2,_1a3);}finally{dojo.setContext(_1a5,_1a6);}return rval;};dojo.withDoc=function(_1a7,_1a8,_1a9,_1aa){var rval;var _1ac=dojo.doc;try{dojo.doc=_1a7;rval=dojo._fireCallback(_1a8,_1a9,_1aa);}finally{dojo.doc=_1ac;}return rval;};}if(!dojo._hasResource["dojo._base.event"]){dojo._hasResource["dojo._base.event"]=true;dojo.provide("dojo._base.event");(function(){var del=(dojo._event_listener={add:function(node,name,fp){if(!node){return;}name=del._normalizeEventName(name);fp=del._fixCallback(name,fp);var _1b1=name;if(!dojo.isIE&&(name=="mouseenter"||name=="mouseleave")){var ofp=fp;name=(name=="mouseenter")?"mouseover":"mouseout";fp=function(e){if(!dojo.isDescendant(e.relatedTarget,node)){return ofp.call(this,e);}};}node.addEventListener(name,fp,false);return fp;},remove:function(node,_1b5,_1b6){if(node){node.removeEventListener(del._normalizeEventName(_1b5),_1b6,false);}},_normalizeEventName:function(name){return name.slice(0,2)=="on"?name.slice(2):name;},_fixCallback:function(name,fp){return name!="keypress"?fp:function(e){return fp.call(this,del._fixEvent(e,this));};},_fixEvent:function(evt,_1bc){switch(evt.type){case "keypress":del._setKeyChar(evt);break;}return evt;},_setKeyChar:function(evt){evt.keyChar=evt.charCode?String.fromCharCode(evt.charCode):"";}});dojo.fixEvent=function(evt,_1bf){return del._fixEvent(evt,_1bf);};dojo.stopEvent=function(evt){evt.preventDefault();evt.stopPropagation();};var _1c1=dojo._listener;dojo._connect=function(obj,_1c3,_1c4,_1c5,_1c6){var _1c7=obj&&(obj.nodeType||obj.attachEvent||obj.addEventListener);var lid=!_1c7?0:(!_1c6?1:2),l=[dojo._listener,del,_1c1][lid];var h=l.add(obj,_1c3,dojo.hitch(_1c4,_1c5));return [obj,_1c3,h,lid];};dojo._disconnect=function(obj,_1cc,_1cd,_1ce){([dojo._listener,del,_1c1][_1ce]).remove(obj,_1cc,_1cd);};dojo.keys={BACKSPACE:8,TAB:9,CLEAR:12,ENTER:13,SHIFT:16,CTRL:17,ALT:18,PAUSE:19,CAPS_LOCK:20,ESCAPE:27,SPACE:32,PAGE_UP:33,PAGE_DOWN:34,END:35,HOME:36,LEFT_ARROW:37,UP_ARROW:38,RIGHT_ARROW:39,DOWN_ARROW:40,INSERT:45,DELETE:46,HELP:47,LEFT_WINDOW:91,RIGHT_WINDOW:92,SELECT:93,NUMPAD_0:96,NUMPAD_1:97,NUMPAD_2:98,NUMPAD_3:99,NUMPAD_4:100,NUMPAD_5:101,NUMPAD_6:102,NUMPAD_7:103,NUMPAD_8:104,NUMPAD_9:105,NUMPAD_MULTIPLY:106,NUMPAD_PLUS:107,NUMPAD_ENTER:108,NUMPAD_MINUS:109,NUMPAD_PERIOD:110,NUMPAD_DIVIDE:111,F1:112,F2:113,F3:114,F4:115,F5:116,F6:117,F7:118,F8:119,F9:120,F10:121,F11:122,F12:123,F13:124,F14:125,F15:126,NUM_LOCK:144,SCROLL_LOCK:145};if(dojo.isIE){var _1cf=function(e,code){try{return (e.keyCode=code);}catch(e){return 0;}};var iel=dojo._listener;if(!dojo.config._allow_leaks){_1c1=iel=dojo._ie_listener={handlers:[],add:function(_1d3,_1d4,_1d5){_1d3=_1d3||dojo.global;var f=_1d3[_1d4];if(!f||!f._listeners){var d=dojo._getIeDispatcher();d.target=f&&(ieh.push(f)-1);d._listeners=[];f=_1d3[_1d4]=d;}return f._listeners.push(ieh.push(_1d5)-1);},remove:function(_1d9,_1da,_1db){var f=(_1d9||dojo.global)[_1da],l=f&&f._listeners;if(f&&l&&_1db--){delete ieh[l[_1db]];delete l[_1db];}}};var ieh=iel.handlers;}dojo.mixin(del,{add:function(node,_1df,fp){if(!node){return;}_1df=del._normalizeEventName(_1df);if(_1df=="onkeypress"){var kd=node.onkeydown;if(!kd||!kd._listeners||!kd._stealthKeydownHandle){var h=del.add(node,"onkeydown",del._stealthKeyDown);kd=node.onkeydown;kd._stealthKeydownHandle=h;kd._stealthKeydownRefs=1;}else{kd._stealthKeydownRefs++;}}return iel.add(node,_1df,del._fixCallback(fp));},remove:function(node,_1e4,_1e5){_1e4=del._normalizeEventName(_1e4);iel.remove(node,_1e4,_1e5);if(_1e4=="onkeypress"){var kd=node.onkeydown;if(--kd._stealthKeydownRefs<=0){iel.remove(node,"onkeydown",kd._stealthKeydownHandle);delete kd._stealthKeydownHandle;}}},_normalizeEventName:function(_1e7){return _1e7.slice(0,2)!="on"?"on"+_1e7:_1e7;},_nop:function(){},_fixEvent:function(evt,_1e9){if(!evt){var w=_1e9&&(_1e9.ownerDocument||_1e9.document||_1e9).parentWindow||window;evt=w.event;}if(!evt){return (evt);}evt.target=evt.srcElement;evt.currentTarget=(_1e9||evt.srcElement);evt.layerX=evt.offsetX;evt.layerY=evt.offsetY;var se=evt.srcElement,doc=(se&&se.ownerDocument)||document;var _1ed=((dojo.isIE<6)||(doc["compatMode"]=="BackCompat"))?doc.body:doc.documentElement;var _1ee=dojo._getIeDocumentElementOffset();evt.pageX=evt.clientX+dojo._fixIeBiDiScrollLeft(_1ed.scrollLeft||0)-_1ee.x;evt.pageY=evt.clientY+(_1ed.scrollTop||0)-_1ee.y;if(evt.type=="mouseover"){evt.relatedTarget=evt.fromElement;}if(evt.type=="mouseout"){evt.relatedTarget=evt.toElement;}evt.stopPropagation=del._stopPropagation;evt.preventDefault=del._preventDefault;return del._fixKeys(evt);},_fixKeys:function(evt){switch(evt.type){case "keypress":var c=("charCode" in evt?evt.charCode:evt.keyCode);if(c==10){c=0;evt.keyCode=13;}else{if(c==13||c==27){c=0;}else{if(c==3){c=99;}}}evt.charCode=c;del._setKeyChar(evt);break;}return evt;},_punctMap:{106:42,111:47,186:59,187:43,188:44,189:45,190:46,191:47,192:96,219:91,220:92,221:93,222:39},_stealthKeyDown:function(evt){var kp=evt.currentTarget.onkeypress;if(!kp||!kp._listeners){return;}var k=evt.keyCode;var _1f4=(k!=13)&&(k!=32)&&(k!=27)&&(k<48||k>90)&&(k<96||k>111)&&(k<186||k>192)&&(k<219||k>222);if(_1f4||evt.ctrlKey){var c=_1f4?0:k;if(evt.ctrlKey){if(k==3||k==13){return;}else{if(c>95&&c<106){c-=48;}else{if((!evt.shiftKey)&&(c>=65&&c<=90)){c+=32;}else{c=del._punctMap[c]||c;}}}}var faux=del._synthesizeEvent(evt,{type:"keypress",faux:true,charCode:c});kp.call(evt.currentTarget,faux);evt.cancelBubble=faux.cancelBubble;evt.returnValue=faux.returnValue;_1cf(evt,faux.keyCode);}},_stopPropagation:function(){this.cancelBubble=true;},_preventDefault:function(){this.bubbledKeyCode=this.keyCode;if(this.ctrlKey){_1cf(this,0);}this.returnValue=false;}});dojo.stopEvent=function(evt){evt=evt||window.event;del._stopPropagation.call(evt);del._preventDefault.call(evt);};}del._synthesizeEvent=function(evt,_1f9){var faux=dojo.mixin({},evt,_1f9);del._setKeyChar(faux);faux.preventDefault=function(){evt.preventDefault();};faux.stopPropagation=function(){evt.stopPropagation();};return faux;};if(dojo.isOpera){dojo.mixin(del,{_fixEvent:function(evt,_1fc){switch(evt.type){case "keypress":var c=evt.which;if(c==3){c=99;}c=((c<41)&&(!evt.shiftKey)?0:c);if((evt.ctrlKey)&&(!evt.shiftKey)&&(c>=65)&&(c<=90)){c+=32;}return del._synthesizeEvent(evt,{charCode:c});}return evt;}});}if(dojo.isSafari){dojo.mixin(del,{_fixEvent:function(evt,_1ff){switch(evt.type){case "keypress":var c=evt.charCode,s=evt.shiftKey,k=evt.keyCode;k=k||_203[evt.keyIdentifier]||0;if(evt.keyIdentifier=="Enter"){c=0;}else{if((evt.ctrlKey)&&(c>0)&&(c<27)){c+=96;}else{if(c==dojo.keys.SHIFT_TAB){c=dojo.keys.TAB;s=true;}else{c=(c>=32&&c<63232?c:0);}}}return del._synthesizeEvent(evt,{charCode:c,shiftKey:s,keyCode:k});}return evt;}});dojo.mixin(dojo.keys,{SHIFT_TAB:25,UP_ARROW:63232,DOWN_ARROW:63233,LEFT_ARROW:63234,RIGHT_ARROW:63235,F1:63236,F2:63237,F3:63238,F4:63239,F5:63240,F6:63241,F7:63242,F8:63243,F9:63244,F10:63245,F11:63246,F12:63247,PAUSE:63250,DELETE:63272,HOME:63273,END:63275,PAGE_UP:63276,PAGE_DOWN:63277,INSERT:63302,PRINT_SCREEN:63248,SCROLL_LOCK:63249,NUM_LOCK:63289});var dk=dojo.keys,_203={"Up":dk.UP_ARROW,"Down":dk.DOWN_ARROW,"Left":dk.LEFT_ARROW,"Right":dk.RIGHT_ARROW,"PageUp":dk.PAGE_UP,"PageDown":dk.PAGE_DOWN};}})();if(dojo.isIE){dojo._ieDispatcher=function(args,_206){var ap=Array.prototype,h=dojo._ie_listener.handlers,c=args.callee,ls=c._listeners,t=h[c.target];var r=t&&t.apply(_206,args);for(var i in ls){if(!(i in ap)){h[ls[i]].apply(_206,args);}}return r;};dojo._getIeDispatcher=function(){return new Function(dojo._scopeName+"._ieDispatcher(arguments, this)");};dojo._event_listener._fixCallback=function(fp){var f=dojo._event_listener._fixEvent;return function(e){return fp.call(this,f(e,this));};};}}if(!dojo._hasResource["dojo._base.html"]){dojo._hasResource["dojo._base.html"]=true;dojo.provide("dojo._base.html");try{document.execCommand("BackgroundImageCache",false,true);}catch(e){}if(dojo.isIE||dojo.isOpera){dojo.byId=function(id,doc){if(dojo.isString(id)){var _d=doc||dojo.doc;var te=_d.getElementById(id);if(te&&te.attributes.id.value==id){return te;}else{var eles=_d.all[id];if(!eles||!eles.length){return eles;}var i=0;while((te=eles[i++])){if(te.attributes.id.value==id){return te;}}}}else{return id;}};}else{dojo.byId=function(id,doc){return dojo.isString(id)?(doc||dojo.doc).getElementById(id):id;};}(function(){var d=dojo;var _21a=null;dojo.addOnUnload(function(){_21a=null;});dojo._destroyElement=function(node){node=d.byId(node);try{if(!_21a){_21a=document.createElement("div");}_21a.appendChild(node.parentNode?node.parentNode.removeChild(node):node);_21a.innerHTML="";}catch(e){}};dojo.isDescendant=function(node,_21d){try{node=d.byId(node);_21d=d.byId(_21d);while(node){if(node===_21d){return true;}node=node.parentNode;}}catch(e){}return false;};dojo.setSelectable=function(node,_21f){node=d.byId(node);if(d.isMozilla){node.style.MozUserSelect=_21f?"":"none";}else{if(d.isKhtml){node.style.KhtmlUserSelect=_21f?"auto":"none";}else{if(d.isIE){node.unselectable=_21f?"":"on";d.query("*",node).forEach(function(_220){_220.unselectable=_21f?"":"on";});}}}};var _221=function(node,ref){ref.parentNode.insertBefore(node,ref);return true;};var _224=function(node,ref){var pn=ref.parentNode;if(ref==pn.lastChild){pn.appendChild(node);}else{return _221(node,ref.nextSibling);}return true;};dojo.place=function(node,_229,_22a){if(!node||!_229||_22a===undefined){return false;}node=d.byId(node);_229=d.byId(_229);if(typeof _22a=="number"){var cn=_229.childNodes;if((_22a==0&&cn.length==0)||cn.length==_22a){_229.appendChild(node);return true;}if(_22a==0){return _221(node,_229.firstChild);}return _224(node,cn[_22a-1]);}switch(_22a.toLowerCase()){case "before":return _221(node,_229);case "after":return _224(node,_229);case "first":if(_229.firstChild){return _221(node,_229.firstChild);}default:_229.appendChild(node);return true;}};dojo.boxModel="content-box";if(d.isIE){var _dcm=document.compatMode;d.boxModel=_dcm=="BackCompat"||_dcm=="QuirksMode"||d.isIE<6?"border-box":"content-box";}var gcs,dv=document.defaultView;if(d.isSafari){gcs=function(node){var s=dv.getComputedStyle(node,null);if(!s&&node.style){node.style.display="";s=dv.getComputedStyle(node,null);}return s||{};};}else{if(d.isIE){gcs=function(node){return node.currentStyle;};}else{gcs=function(node){return dv.getComputedStyle(node,null);};}}dojo.getComputedStyle=gcs;if(!d.isIE){dojo._toPixelValue=function(_233,_234){return parseFloat(_234)||0;};}else{dojo._toPixelValue=function(_235,_236){if(!_236){return 0;}if(_236=="medium"){return 4;}if(_236.slice&&(_236.slice(-2)=="px")){return parseFloat(_236);}with(_235){var _237=style.left;var _238=runtimeStyle.left;runtimeStyle.left=currentStyle.left;try{style.left=_236;_236=style.pixelLeft;}catch(e){_236=0;}style.left=_237;runtimeStyle.left=_238;}return _236;};}var px=d._toPixelValue;dojo._getOpacity=d.isIE?function(node){try{return node.filters.alpha.opacity/100;}catch(e){return 1;}}:function(node){return gcs(node).opacity;};dojo._setOpacity=d.isIE?function(node,_23d){if(_23d==1){var _23e=/FILTER:[^;]*;?/i;node.style.cssText=node.style.cssText.replace(_23e,"");if(node.nodeName.toLowerCase()=="tr"){d.query("> td",node).forEach(function(i){i.style.cssText=i.style.cssText.replace(_23e,"");});}}else{var o="Alpha(Opacity="+_23d*100+")";node.style.filter=o;}if(node.nodeName.toLowerCase()=="tr"){d.query("> td",node).forEach(function(i){i.style.filter=o;});}return _23d;}:function(node,_243){return node.style.opacity=_243;};var _244={left:true,top:true};var _245=/margin|padding|width|height|max|min|offset/;var _246=function(node,type,_249){type=type.toLowerCase();if(d.isIE&&_249=="auto"){if(type=="height"){return node.offsetHeight;}if(type=="width"){return node.offsetWidth;}}if(!(type in _244)){_244[type]=_245.test(type);}return _244[type]?px(node,_249):_249;};var _24a=d.isIE?"styleFloat":"cssFloat";var _24b={"cssFloat":_24a,"styleFloat":_24a,"float":_24a};dojo.style=function(node,_24d,_24e){var n=d.byId(node),args=arguments.length,op=(_24d=="opacity");_24d=_24b[_24d]||_24d;if(args==3){return op?d._setOpacity(n,_24e):n.style[_24d]=_24e;}if(args==2&&op){return d._getOpacity(n);}var s=gcs(n);if(args==2&&!d.isString(_24d)){for(var x in _24d){d.style(node,x,_24d[x]);}return s;}return (args==1)?s:_246(n,_24d,s[_24d]);};dojo._getPadExtents=function(n,_255){var s=_255||gcs(n),l=px(n,s.paddingLeft),t=px(n,s.paddingTop);return {l:l,t:t,w:l+px(n,s.paddingRight),h:t+px(n,s.paddingBottom)};};dojo._getBorderExtents=function(n,_25a){var ne="none",s=_25a||gcs(n),bl=(s.borderLeftStyle!=ne?px(n,s.borderLeftWidth):0),bt=(s.borderTopStyle!=ne?px(n,s.borderTopWidth):0);return {l:bl,t:bt,w:bl+(s.borderRightStyle!=ne?px(n,s.borderRightWidth):0),h:bt+(s.borderBottomStyle!=ne?px(n,s.borderBottomWidth):0)};};dojo._getPadBorderExtents=function(n,_260){var s=_260||gcs(n),p=d._getPadExtents(n,s),b=d._getBorderExtents(n,s);return {l:p.l+b.l,t:p.t+b.t,w:p.w+b.w,h:p.h+b.h};};dojo._getMarginExtents=function(n,_265){var s=_265||gcs(n),l=px(n,s.marginLeft),t=px(n,s.marginTop),r=px(n,s.marginRight),b=px(n,s.marginBottom);if(d.isSafari&&(s.position!="absolute")){r=l;}return {l:l,t:t,w:l+r,h:t+b};};dojo._getMarginBox=function(node,_26c){var s=_26c||gcs(node),me=d._getMarginExtents(node,s);var l=node.offsetLeft-me.l,t=node.offsetTop-me.t;if(d.isMoz){var sl=parseFloat(s.left),st=parseFloat(s.top);if(!isNaN(sl)&&!isNaN(st)){l=sl,t=st;}else{var p=node.parentNode;if(p&&p.style){var pcs=gcs(p);if(pcs.overflow!="visible"){var be=d._getBorderExtents(p,pcs);l+=be.l,t+=be.t;}}}}else{if(d.isOpera){var p=node.parentNode;if(p){var be=d._getBorderExtents(p);l-=be.l,t-=be.t;}}}return {l:l,t:t,w:node.offsetWidth+me.w,h:node.offsetHeight+me.h};};dojo._getContentBox=function(node,_277){var s=_277||gcs(node),pe=d._getPadExtents(node,s),be=d._getBorderExtents(node,s),w=node.clientWidth,h;if(!w){w=node.offsetWidth,h=node.offsetHeight;}else{h=node.clientHeight,be.w=be.h=0;}if(d.isOpera){pe.l+=be.l;pe.t+=be.t;}return {l:pe.l,t:pe.t,w:w-pe.w-be.w,h:h-pe.h-be.h};};dojo._getBorderBox=function(node,_27e){var s=_27e||gcs(node),pe=d._getPadExtents(node,s),cb=d._getContentBox(node,s);return {l:cb.l-pe.l,t:cb.t-pe.t,w:cb.w+pe.w,h:cb.h+pe.h};};dojo._setBox=function(node,l,t,w,h,u){u=u||"px";var s=node.style;if(!isNaN(l)){s.left=l+u;}if(!isNaN(t)){s.top=t+u;}if(w>=0){s.width=w+u;}if(h>=0){s.height=h+u;}};dojo._usesBorderBox=function(node){var n=node.tagName;return d.boxModel=="border-box"||n=="TABLE"||n=="BUTTON";};dojo._setContentSize=function(node,_28c,_28d,_28e){if(d._usesBorderBox(node)){var pb=d._getPadBorderExtents(node,_28e);if(_28c>=0){_28c+=pb.w;}if(_28d>=0){_28d+=pb.h;}}d._setBox(node,NaN,NaN,_28c,_28d);};dojo._setMarginBox=function(node,_291,_292,_293,_294,_295){var s=_295||gcs(node);var bb=d._usesBorderBox(node),pb=bb?_299:d._getPadBorderExtents(node,s),mb=d._getMarginExtents(node,s);if(_293>=0){_293=Math.max(_293-pb.w-mb.w,0);}if(_294>=0){_294=Math.max(_294-pb.h-mb.h,0);}d._setBox(node,_291,_292,_293,_294);};var _299={l:0,t:0,w:0,h:0};dojo.marginBox=function(node,box){var n=d.byId(node),s=gcs(n),b=box;return !b?d._getMarginBox(n,s):d._setMarginBox(n,b.l,b.t,b.w,b.h,s);};dojo.contentBox=function(node,box){var n=dojo.byId(node),s=gcs(n),b=box;return !b?d._getContentBox(n,s):d._setContentSize(n,b.w,b.h,s);};var _2a5=function(node,prop){if(!(node=(node||0).parentNode)){return 0;}var val,_2a9=0,_b=d.body();while(node&&node.style){if(gcs(node).position=="fixed"){return 0;}val=node[prop];if(val){_2a9+=val-0;if(node==_b){break;}}node=node.parentNode;}return _2a9;};dojo._docScroll=function(){var _b=d.body(),_w=d.global,de=d.doc.documentElement;return {y:(_w.pageYOffset||de.scrollTop||_b.scrollTop||0),x:(_w.pageXOffset||d._fixIeBiDiScrollLeft(de.scrollLeft)||_b.scrollLeft||0)};};dojo._isBodyLtr=function(){return !("_bodyLtr" in d)?d._bodyLtr=gcs(d.body()).direction=="ltr":d._bodyLtr;};dojo._getIeDocumentElementOffset=function(){var de=d.doc.documentElement;return (d.isIE>=7)?{x:de.getBoundingClientRect().left,y:de.getBoundingClientRect().top}:{x:d._isBodyLtr()||window.parent==window?de.clientLeft:de.offsetWidth-de.clientWidth-de.clientLeft,y:de.clientTop};};dojo._fixIeBiDiScrollLeft=function(_2af){var dd=d.doc;if(d.isIE&&!dojo._isBodyLtr()){var de=dd.compatMode=="BackCompat"?dd.body:dd.documentElement;return _2af+de.clientWidth-de.scrollWidth;}return _2af;};dojo._abs=function(node,_2b3){var _2b4=node.ownerDocument;var ret={x:0,y:0};var db=d.body();if(d.isIE||(d.isFF>=3)){var _2b7=node.getBoundingClientRect();var _2b8=(d.isIE)?d._getIeDocumentElementOffset():{x:0,y:0};ret.x=_2b7.left-_2b8.x;ret.y=_2b7.top-_2b8.y;}else{if(_2b4["getBoxObjectFor"]){var bo=_2b4.getBoxObjectFor(node),b=d._getBorderExtents(node);ret.x=bo.x-b.l-_2a5(node,"scrollLeft");ret.y=bo.y-b.t-_2a5(node,"scrollTop");}else{if(node["offsetParent"]){var _2bb;if(d.isSafari&&(gcs(node).position=="absolute")&&(node.parentNode==db)){_2bb=db;}else{_2bb=db.parentNode;}if(node.parentNode!=db){var nd=node;if(d.isOpera){nd=db;}ret.x-=_2a5(nd,"scrollLeft");ret.y-=_2a5(nd,"scrollTop");}var _2bd=node;do{var n=_2bd.offsetLeft;if(!d.isOpera||n>0){ret.x+=isNaN(n)?0:n;}var t=_2bd.offsetTop;ret.y+=isNaN(t)?0:t;if(d.isSafari&&_2bd!=node){var cs=gcs(_2bd);ret.x+=px(_2bd,cs.borderLeftWidth);ret.y+=px(_2bd,cs.borderTopWidth);}_2bd=_2bd.offsetParent;}while((_2bd!=_2bb)&&_2bd);}else{if(node.x&&node.y){ret.x+=isNaN(node.x)?0:node.x;ret.y+=isNaN(node.y)?0:node.y;}}}}if(_2b3){var _2c1=d._docScroll();ret.y+=_2c1.y;ret.x+=_2c1.x;}return ret;};dojo.coords=function(node,_2c3){var n=d.byId(node),s=gcs(n),mb=d._getMarginBox(n,s);var abs=d._abs(n,_2c3);mb.x=abs.x;mb.y=abs.y;return mb;};var _2c8=function(name){switch(name.toLowerCase()){case "tabindex":return (d.isIE&&d.isIE<8)?"tabIndex":"tabindex";default:return name;}};var _2ca={colspan:"colSpan",enctype:"enctype",frameborder:"frameborder",method:"method",rowspan:"rowSpan",scrolling:"scrolling",shape:"shape",span:"span",type:"type",valuetype:"valueType"};dojo.hasAttr=function(node,name){var attr=d.byId(node).getAttributeNode(_2c8(name));return attr?attr.specified:false;};var _2ce={};var _ctr=0;var _2d0=dojo._scopeName+"attrid";dojo.attr=function(node,name,_2d3){var args=arguments.length;if(args==2&&!d.isString(name)){for(var x in name){d.attr(node,x,name[x]);}return;}node=d.byId(node);name=_2c8(name);if(args==3){if(d.isFunction(_2d3)){var _2d6=d.attr(node,_2d0);if(!_2d6){_2d6=_ctr++;d.attr(node,_2d0,_2d6);}if(!_2ce[_2d6]){_2ce[_2d6]={};}var h=_2ce[_2d6][name];if(h){d.disconnect(h);}else{try{delete node[name];}catch(e){}}_2ce[_2d6][name]=d.connect(node,name,_2d3);}else{if(typeof _2d3=="boolean"){node[name]=_2d3;}else{node.setAttribute(name,_2d3);}}return;}else{var prop=_2ca[name.toLowerCase()];if(prop){return node[prop];}else{var _2d3=node[name];return (typeof _2d3=="boolean"||typeof _2d3=="function")?_2d3:(d.hasAttr(node,name)?node.getAttribute(name):null);}}};dojo.removeAttr=function(node,name){d.byId(node).removeAttribute(_2c8(name));};})();dojo.hasClass=function(node,_2dc){return ((" "+dojo.byId(node).className+" ").indexOf(" "+_2dc+" ")>=0);};dojo.addClass=function(node,_2de){node=dojo.byId(node);var cls=node.className;if((" "+cls+" ").indexOf(" "+_2de+" ")<0){node.className=cls+(cls?" ":"")+_2de;}};dojo.removeClass=function(node,_2e1){node=dojo.byId(node);var t=dojo.trim((" "+node.className+" ").replace(" "+_2e1+" "," "));if(node.className!=t){node.className=t;}};dojo.toggleClass=function(node,_2e4,_2e5){if(_2e5===undefined){_2e5=!dojo.hasClass(node,_2e4);}dojo[_2e5?"addClass":"removeClass"](node,_2e4);};}if(!dojo._hasResource["dojo._base.NodeList"]){dojo._hasResource["dojo._base.NodeList"]=true;dojo.provide("dojo._base.NodeList");(function(){var d=dojo;var tnl=function(arr){arr.constructor=dojo.NodeList;dojo._mixin(arr,dojo.NodeList.prototype);return arr;};var _2e9=function(func,_2eb){return function(){var _a=arguments;var aa=d._toArray(_a,0,[null]);var s=this.map(function(i){aa[0]=i;return d[func].apply(d,aa);});return (_2eb||((_a.length>1)||!d.isString(_a[0])))?this:s;};};dojo.NodeList=function(){return tnl(Array.apply(null,arguments));};dojo.NodeList._wrap=tnl;dojo.extend(dojo.NodeList,{slice:function(){var a=dojo._toArray(arguments);return tnl(a.slice.apply(this,a));},splice:function(){var a=dojo._toArray(arguments);return tnl(a.splice.apply(this,a));},concat:function(){var a=dojo._toArray(arguments,0,[this]);return tnl(a.concat.apply([],a));},indexOf:function(_2f3,_2f4){return d.indexOf(this,_2f3,_2f4);},lastIndexOf:function(){return d.lastIndexOf.apply(d,d._toArray(arguments,0,[this]));},every:function(_2f5,_2f6){return d.every(this,_2f5,_2f6);},some:function(_2f7,_2f8){return d.some(this,_2f7,_2f8);},map:function(func,obj){return d.map(this,func,obj,d.NodeList);},forEach:function(_2fb,_2fc){d.forEach(this,_2fb,_2fc);return this;},coords:function(){return d.map(this,d.coords);},attr:_2e9("attr"),style:_2e9("style"),addClass:_2e9("addClass",true),removeClass:_2e9("removeClass",true),toggleClass:_2e9("toggleClass",true),connect:_2e9("connect",true),place:function(_2fd,_2fe){var item=d.query(_2fd)[0];return this.forEach(function(i){d.place(i,item,(_2fe||"last"));});},orphan:function(_301){var _302=_301?d._filterQueryResult(this,_301):this;_302.forEach(function(item){if(item.parentNode){item.parentNode.removeChild(item);}});return _302;},adopt:function(_304,_305){var item=this[0];return d.query(_304).forEach(function(ai){d.place(ai,item,_305||"last");});},query:function(_308){if(!_308){return this;}var ret=d.NodeList();this.forEach(function(item){d.query(_308,item).forEach(function(_30b){if(_30b!==undefined){ret.push(_30b);}});});return ret;},filter:function(_30c){var _30d=this;var _a=arguments;var r=d.NodeList();var rp=function(t){if(t!==undefined){r.push(t);}};if(d.isString(_30c)){_30d=d._filterQueryResult(this,_a[0]);if(_a.length==1){return _30d;}_a.shift();}d.forEach(d.filter(_30d,_a[0],_a[1]),rp);return r;},addContent:function(_312,_313){var ta=d.doc.createElement("span");if(d.isString(_312)){ta.innerHTML=_312;}else{ta.appendChild(_312);}if(_313===undefined){_313="last";}var ct=(_313=="first"||_313=="after")?"lastChild":"firstChild";this.forEach(function(item){var tn=ta.cloneNode(true);while(tn[ct]){d.place(tn[ct],item,_313);}});return this;},empty:function(){return this.forEach("item.innerHTML='';");},instantiate:function(_318,_319){var c=d.isFunction(_318)?_318:d.getObject(_318);return this.forEach(function(i){new c(_319||{},i);});}});d.forEach(["blur","focus","click","keydown","keypress","keyup","mousedown","mouseenter","mouseleave","mousemove","mouseout","mouseover","mouseup"],function(evt){var _oe="on"+evt;dojo.NodeList.prototype[_oe]=function(a,b){return this.connect(_oe,a,b);};});})();}if(!dojo._hasResource["dojo._base.query"]){dojo._hasResource["dojo._base.query"]=true;dojo.provide("dojo._base.query");(function(){var d=dojo;var _321=dojo.isIE?"children":"childNodes";var _322=false;var _323=function(_324){if(">~+".indexOf(_324.charAt(_324.length-1))>=0){_324+=" *";}_324+=" ";var ts=function(s,e){return d.trim(_324.slice(s,e));};var _328=[];var _329=-1;var _32a=-1;var _32b=-1;var _32c=-1;var _32d=-1;var inId=-1;var _32f=-1;var lc="";var cc="";var _332;var x=0;var ql=_324.length;var _335=null;var _cp=null;var _337=function(){if(_32f>=0){var tv=(_32f==x)?null:ts(_32f,x).toLowerCase();_335[(">~+".indexOf(tv)<0)?"tag":"oper"]=tv;_32f=-1;}};var _339=function(){if(inId>=0){_335.id=ts(inId,x).replace(/\\/g,"");inId=-1;}};var _33a=function(){if(_32d>=0){_335.classes.push(ts(_32d+1,x).replace(/\\/g,""));_32d=-1;}};var _33b=function(){_339();_337();_33a();};for(;lc=cc,cc=_324.charAt(x),x<ql;x++){if(lc=="\\"){continue;}if(!_335){_332=x;_335={query:null,pseudos:[],attrs:[],classes:[],tag:null,oper:null,id:null};_32f=x;}if(_329>=0){if(cc=="]"){if(!_cp.attr){_cp.attr=ts(_329+1,x);}else{_cp.matchFor=ts((_32b||_329+1),x);}var cmf=_cp.matchFor;if(cmf){if((cmf.charAt(0)=="\"")||(cmf.charAt(0)=="'")){_cp.matchFor=cmf.substring(1,cmf.length-1);}}_335.attrs.push(_cp);_cp=null;_329=_32b=-1;}else{if(cc=="="){var _33d=("|~^$*".indexOf(lc)>=0)?lc:"";_cp.type=_33d+cc;_cp.attr=ts(_329+1,x-_33d.length);_32b=x+1;}}}else{if(_32a>=0){if(cc==")"){if(_32c>=0){_cp.value=ts(_32a+1,x);}_32c=_32a=-1;}}else{if(cc=="#"){_33b();inId=x+1;}else{if(cc=="."){_33b();_32d=x;}else{if(cc==":"){_33b();_32c=x;}else{if(cc=="["){_33b();_329=x;_cp={};}else{if(cc=="("){if(_32c>=0){_cp={name:ts(_32c+1,x),value:null};_335.pseudos.push(_cp);}_32a=x;}else{if(cc==" "&&lc!=cc){_33b();if(_32c>=0){_335.pseudos.push({name:ts(_32c+1,x)});}_335.hasLoops=(_335.pseudos.length||_335.attrs.length||_335.classes.length);_335.query=ts(_332,x);_335.tag=(_335["oper"])?null:(_335.tag||"*");_328.push(_335);_335=null;}}}}}}}}}return _328;};var _33e={"*=":function(attr,_340){return "[contains(@"+attr+", '"+_340+"')]";},"^=":function(attr,_342){return "[starts-with(@"+attr+", '"+_342+"')]";},"$=":function(attr,_344){return "[substring(@"+attr+", string-length(@"+attr+")-"+(_344.length-1)+")='"+_344+"']";},"~=":function(attr,_346){return "[contains(concat(' ',@"+attr+",' '), ' "+_346+" ')]";},"|=":function(attr,_348){return "[contains(concat(' ',@"+attr+",' '), ' "+_348+"-')]";},"=":function(attr,_34a){return "[@"+attr+"='"+_34a+"']";}};var _34b=function(_34c,_34d,_34e,_34f){d.forEach(_34d.attrs,function(attr){var _351;if(attr.type&&_34c[attr.type]){_351=_34c[attr.type](attr.attr,attr.matchFor);}else{if(attr.attr.length){_351=_34e(attr.attr);}}if(_351){_34f(_351);}});};var _352=function(_353){var _354=".";var _355=_323(d.trim(_353));while(_355.length){var tqp=_355.shift();var _357;var _358="";if(tqp.oper==">"){_357="/";tqp=_355.shift();}else{if(tqp.oper=="~"){_357="/following-sibling::";tqp=_355.shift();}else{if(tqp.oper=="+"){_357="/following-sibling::";_358="[position()=1]";tqp=_355.shift();}else{_357="//";}}}_354+=_357+tqp.tag+_358;if(tqp.id){_354+="[@id='"+tqp.id+"'][1]";}d.forEach(tqp.classes,function(cn){var cnl=cn.length;var _35b=" ";if(cn.charAt(cnl-1)=="*"){_35b="";cn=cn.substr(0,cnl-1);}_354+="[contains(concat(' ',@class,' '), ' "+cn+_35b+"')]";});_34b(_33e,tqp,function(_35c){return "[@"+_35c+"]";},function(_35d){_354+=_35d;});}return _354;};var _35e={};var _35f=function(path){if(_35e[path]){return _35e[path];}var doc=d.doc;var _362=_352(path);var tf=function(_364){var ret=[];var _366;try{_366=doc.evaluate(_362,_364,null,XPathResult.ANY_TYPE,null);}catch(e){console.debug("failure in exprssion:",_362,"under:",_364);console.debug(e);}var _367=_366.iterateNext();while(_367){ret.push(_367);_367=_366.iterateNext();}return ret;};return _35e[path]=tf;};var _368={};var _369={};var _36a=function(_36b,_36c){if(!_36b){return _36c;}if(!_36c){return _36b;}return function(){return _36b.apply(window,arguments)&&_36c.apply(window,arguments);};};var _36d=function(root){var ret=[];var te,x=0,tret=root[_321];while(te=tret[x++]){if(te.nodeType==1){ret.push(te);}}return ret;};var _373=function(root,_375){var ret=[];var te=root;while(te=te.nextSibling){if(te.nodeType==1){ret.push(te);if(_375){break;}}}return ret;};var _378=function(_379,_37a,_37b,idx){var nidx=idx+1;var _37e=(_37a.length==nidx);var tqp=_37a[idx];if(tqp.oper){var ecn=(tqp.oper==">")?_36d(_379):_373(_379,(tqp.oper=="+"));if(!ecn||!ecn.length){return;}nidx++;_37e=(_37a.length==nidx);var tf=_382(_37a[idx+1]);for(var x=0,ecnl=ecn.length,te;x<ecnl,te=ecn[x];x++){if(tf(te)){if(_37e){_37b.push(te);}else{_378(te,_37a,_37b,nidx);}}}}var _386=_387(tqp)(_379);if(_37e){while(_386.length){_37b.push(_386.shift());}}else{while(_386.length){_378(_386.shift(),_37a,_37b,nidx);}}};var _388=function(_389,_38a){var ret=[];var x=_389.length-1,te;while(te=_389[x--]){_378(te,_38a,ret,0);}return ret;};var _382=function(q){if(_368[q.query]){return _368[q.query];}var ff=null;if(q.tag){if(q.tag=="*"){ff=_36a(ff,function(elem){return (elem.nodeType==1);});}else{ff=_36a(ff,function(elem){return ((elem.nodeType==1)&&(q.tag==elem.tagName.toLowerCase()));});}}if(q.id){ff=_36a(ff,function(elem){return ((elem.nodeType==1)&&(elem.id==q.id));});}if(q.hasLoops){ff=_36a(ff,_393(q));}return _368[q.query]=ff;};var _394=function(node){var pn=node.parentNode;var pnc=pn.childNodes;var nidx=-1;var _399=pn.firstChild;if(!_399){return nidx;}var ci=node["__cachedIndex"];var cl=pn["__cachedLength"];if(((typeof cl=="number")&&(cl!=pnc.length))||(typeof ci!="number")){pn["__cachedLength"]=pnc.length;var idx=1;do{if(_399===node){nidx=idx;}if(_399.nodeType==1){_399["__cachedIndex"]=idx;idx++;}_399=_399.nextSibling;}while(_399);}else{nidx=ci;}return nidx;};var _39d=0;var _39e="";var _39f=function(elem,attr){if(attr=="class"){return elem.className||_39e;}if(attr=="for"){return elem.htmlFor||_39e;}return elem.getAttribute(attr,2)||_39e;};var _3a2={"*=":function(attr,_3a4){return function(elem){return (_39f(elem,attr).indexOf(_3a4)>=0);};},"^=":function(attr,_3a7){return function(elem){return (_39f(elem,attr).indexOf(_3a7)==0);};},"$=":function(attr,_3aa){var tval=" "+_3aa;return function(elem){var ea=" "+_39f(elem,attr);return (ea.lastIndexOf(_3aa)==(ea.length-_3aa.length));};},"~=":function(attr,_3af){var tval=" "+_3af+" ";return function(elem){var ea=" "+_39f(elem,attr)+" ";return (ea.indexOf(tval)>=0);};},"|=":function(attr,_3b4){var _3b5=" "+_3b4+"-";return function(elem){var ea=" "+(elem.getAttribute(attr,2)||"");return ((ea==_3b4)||(ea.indexOf(_3b5)==0));};},"=":function(attr,_3b9){return function(elem){return (_39f(elem,attr)==_3b9);};}};var _3bb={"first-child":function(name,_3bd){return function(elem){if(elem.nodeType!=1){return false;}var fc=elem.previousSibling;while(fc&&(fc.nodeType!=1)){fc=fc.previousSibling;}return (!fc);};},"last-child":function(name,_3c1){return function(elem){if(elem.nodeType!=1){return false;}var nc=elem.nextSibling;while(nc&&(nc.nodeType!=1)){nc=nc.nextSibling;}return (!nc);};},"empty":function(name,_3c5){return function(elem){var cn=elem.childNodes;var cnl=elem.childNodes.length;for(var x=cnl-1;x>=0;x--){var nt=cn[x].nodeType;if((nt==1)||(nt==3)){return false;}}return true;};},"contains":function(name,_3cc){return function(elem){return (elem.innerHTML.indexOf(_3cc)>=0);};},"not":function(name,_3cf){var ntf=_382(_323(_3cf)[0]);return function(elem){return (!ntf(elem));};},"nth-child":function(name,_3d3){var pi=parseInt;if(_3d3=="odd"){return function(elem){return (((_394(elem))%2)==1);};}else{if((_3d3=="2n")||(_3d3=="even")){return function(elem){return ((_394(elem)%2)==0);};}else{if(_3d3.indexOf("0n+")==0){var _3d7=pi(_3d3.substr(3));return function(elem){return (elem.parentNode[_321][_3d7-1]===elem);};}else{if((_3d3.indexOf("n+")>0)&&(_3d3.length>3)){var _3d9=_3d3.split("n+",2);var pred=pi(_3d9[0]);var idx=pi(_3d9[1]);return function(elem){return ((_394(elem)%pred)==idx);};}else{if(_3d3.indexOf("n")==-1){var _3d7=pi(_3d3);return function(elem){return (_394(elem)==_3d7);};}}}}}}};var _3de=(d.isIE)?function(cond){var clc=cond.toLowerCase();return function(elem){return elem[cond]||elem[clc];};}:function(cond){return function(elem){return (elem&&elem.getAttribute&&elem.hasAttribute(cond));};};var _393=function(_3e4){var _3e5=(_369[_3e4.query]||_368[_3e4.query]);if(_3e5){return _3e5;}var ff=null;if(_3e4.id){if(_3e4.tag!="*"){ff=_36a(ff,function(elem){return (elem.tagName.toLowerCase()==_3e4.tag);});}}d.forEach(_3e4.classes,function(_3e8,idx,arr){var _3eb=_3e8.charAt(_3e8.length-1)=="*";if(_3eb){_3e8=_3e8.substr(0,_3e8.length-1);}var re=new RegExp("(?:^|\\s)"+_3e8+(_3eb?".*":"")+"(?:\\s|$)");ff=_36a(ff,function(elem){return re.test(elem.className);});ff.count=idx;});d.forEach(_3e4.pseudos,function(_3ee){if(_3bb[_3ee.name]){ff=_36a(ff,_3bb[_3ee.name](_3ee.name,_3ee.value));}});_34b(_3a2,_3e4,_3de,function(_3ef){ff=_36a(ff,_3ef);});if(!ff){ff=function(){return true;};}return _369[_3e4.query]=ff;};var _3f0={};var _387=function(_3f1,root){var fHit=_3f0[_3f1.query];if(fHit){return fHit;}if(_3f1.id&&!_3f1.hasLoops&&!_3f1.tag){return _3f0[_3f1.query]=function(root){return [d.byId(_3f1.id)];};}var _3f5=_393(_3f1);var _3f6;if(_3f1.tag&&_3f1.id&&!_3f1.hasLoops){_3f6=function(root){var te=d.byId(_3f1.id);if(_3f5(te)){return [te];}};}else{var tret;if(!_3f1.hasLoops){_3f6=function(root){var ret=[];var te,x=0,tret=root.getElementsByTagName(_3f1.tag);while(te=tret[x++]){ret.push(te);}return ret;};}else{_3f6=function(root){var ret=[];var te,x=0,tret=root.getElementsByTagName(_3f1.tag);while(te=tret[x++]){if(_3f5(te)){ret.push(te);}}return ret;};}}return _3f0[_3f1.query]=_3f6;};var _402={};var _403={"*":d.isIE?function(root){return root.all;}:function(root){return root.getElementsByTagName("*");},"~":_373,"+":function(root){return _373(root,true);},">":_36d};var _407=function(_408){var _409=_323(d.trim(_408));if(_409.length==1){var tt=_387(_409[0]);tt.nozip=true;return tt;}var sqf=function(root){var _40d=_409.slice(0);var _40e;if(_40d[0].oper==">"){_40e=[root];}else{_40e=_387(_40d.shift())(root);}return _388(_40e,_40d);};return sqf;};var _40f=((document["evaluate"]&&!d.isSafari)?function(_410){var _411=_410.split(" ");if((document["evaluate"])&&(_410.indexOf(":")==-1)&&(_410.indexOf("+")==-1)){if(((_411.length>2)&&(_410.indexOf(">")==-1))||(_411.length>3)||(_410.indexOf("[")>=0)||((1==_411.length)&&(0<=_410.indexOf(".")))){return _35f(_410);}}return _407(_410);}:_407);var _412=function(_413){var qcz=_413.charAt(0);if(d.doc["querySelectorAll"]&&((!d.isSafari)||(d.isSafari>3.1))&&(">+~".indexOf(qcz)==-1)){return function(root){var r=root.querySelectorAll(_413);r.nozip=true;return r;};}if(_403[_413]){return _403[_413];}if(0>_413.indexOf(",")){return _403[_413]=_40f(_413);}else{var _417=_413.split(/\s*,\s*/);var tf=function(root){var _41a=0;var ret=[];var tp;while(tp=_417[_41a++]){ret=ret.concat(_40f(tp,tp.indexOf(" "))(root));}return ret;};return _403[_413]=tf;}};var _41d=0;var _zip=function(arr){if(arr&&arr.nozip){return d.NodeList._wrap(arr);}var ret=new d.NodeList();if(!arr){return ret;}if(arr[0]){ret.push(arr[0]);}if(arr.length<2){return ret;}_41d++;arr[0]["_zipIdx"]=_41d;for(var x=1,te;te=arr[x];x++){if(arr[x]["_zipIdx"]!=_41d){ret.push(te);}te["_zipIdx"]=_41d;}return ret;};d.query=function(_423,root){if(_423.constructor==d.NodeList){return _423;}if(!d.isString(_423)){return new d.NodeList(_423);}if(d.isString(root)){root=d.byId(root);}return _zip(_412(_423)(root||d.doc));};d.query.pseudos=_3bb;d._filterQueryResult=function(_425,_426){var tnl=new d.NodeList();var ff=(_426)?_382(_323(_426)[0]):function(){return true;};for(var x=0,te;te=_425[x];x++){if(ff(te)){tnl.push(te);}}return tnl;};})();}if(!dojo._hasResource["dojo._base.xhr"]){dojo._hasResource["dojo._base.xhr"]=true;dojo.provide("dojo._base.xhr");(function(){var _d=dojo;function setValue(obj,name,_42e){var val=obj[name];if(_d.isString(val)){obj[name]=[val,_42e];}else{if(_d.isArray(val)){val.push(_42e);}else{obj[name]=_42e;}}};dojo.formToObject=function(_430){var ret={};var iq="input:not([type=file]):not([type=submit]):not([type=image]):not([type=reset]):not([type=button]), select, textarea";_d.query(iq,_430).filter(function(node){return !node.disabled&&node.name;}).forEach(function(item){var _in=item.name;var type=(item.type||"").toLowerCase();if(type=="radio"||type=="checkbox"){if(item.checked){setValue(ret,_in,item.value);}}else{if(item.multiple){ret[_in]=[];_d.query("option",item).forEach(function(opt){if(opt.selected){setValue(ret,_in,opt.value);}});}else{setValue(ret,_in,item.value);if(type=="image"){ret[_in+".x"]=ret[_in+".y"]=ret[_in].x=ret[_in].y=0;}}}});return ret;};dojo.objectToQuery=function(map){var enc=encodeURIComponent;var _43a=[];var _43b={};for(var name in map){var _43d=map[name];if(_43d!=_43b[name]){var _43e=enc(name)+"=";if(_d.isArray(_43d)){for(var i=0;i<_43d.length;i++){_43a.push(_43e+enc(_43d[i]));}}else{_43a.push(_43e+enc(_43d));}}}return _43a.join("&");};dojo.formToQuery=function(_440){return _d.objectToQuery(_d.formToObject(_440));};dojo.formToJson=function(_441,_442){return _d.toJson(_d.formToObject(_441),_442);};dojo.queryToObject=function(str){var ret={};var qp=str.split("&");var dec=decodeURIComponent;_d.forEach(qp,function(item){if(item.length){var _448=item.split("=");var name=dec(_448.shift());var val=dec(_448.join("="));if(_d.isString(ret[name])){ret[name]=[ret[name]];}if(_d.isArray(ret[name])){ret[name].push(val);}else{ret[name]=val;}}});return ret;};dojo._blockAsync=false;dojo._contentHandlers={"text":function(xhr){return xhr.responseText;},"json":function(xhr){if(!dojo.config.usePlainJson){console.warn("Consider using mimetype:text/json-comment-filtered"+" to avoid potential security issues with JSON endpoints"+" (use djConfig.usePlainJson=true to turn off this message)");}return (xhr.status==204)?undefined:_d.fromJson(xhr.responseText);},"json-comment-filtered":function(xhr){var _44e=xhr.responseText;var _44f=_44e.indexOf("/*");var _450=_44e.lastIndexOf("*/");if(_44f==-1||_450==-1){throw new Error("JSON was not comment filtered");}return (xhr.status==204)?undefined:_d.fromJson(_44e.substring(_44f+2,_450));},"javascript":function(xhr){return _d.eval(xhr.responseText);},"xml":function(xhr){var _453=xhr.responseXML;if(_d.isIE&&(!_453||window.location.protocol=="file:")){_d.forEach(["MSXML2","Microsoft","MSXML","MSXML3"],function(_454){try{var dom=new ActiveXObject(_454+".XMLDOM");dom.async=false;dom.loadXML(xhr.responseText);_453=dom;}catch(e){}});}return _453;}};dojo._contentHandlers["json-comment-optional"]=function(xhr){var _457=_d._contentHandlers;try{return _457["json-comment-filtered"](xhr);}catch(e){return _457["json"](xhr);}};dojo._ioSetArgs=function(args,_459,_45a,_45b){var _45c={args:args,url:args.url};var _45d=null;if(args.form){var form=_d.byId(args.form);var _45f=form.getAttributeNode("action");_45c.url=_45c.url||(_45f?_45f.value:null);_45d=_d.formToObject(form);}var _460=[{}];if(_45d){_460.push(_45d);}if(args.content){_460.push(args.content);}if(args.preventCache){_460.push({"dojo.preventCache":new Date().valueOf()});}_45c.query=_d.objectToQuery(_d.mixin.apply(null,_460));_45c.handleAs=args.handleAs||"text";var d=new _d.Deferred(_459);d.addCallbacks(_45a,function(_462){return _45b(_462,d);});var ld=args.load;if(ld&&_d.isFunction(ld)){d.addCallback(function(_464){return ld.call(args,_464,_45c);});}var err=args.error;if(err&&_d.isFunction(err)){d.addErrback(function(_466){return err.call(args,_466,_45c);});}var _467=args.handle;if(_467&&_d.isFunction(_467)){d.addBoth(function(_468){return _467.call(args,_468,_45c);});}d.ioArgs=_45c;return d;};var _469=function(dfd){dfd.canceled=true;var xhr=dfd.ioArgs.xhr;var _at=typeof xhr.abort;if(_at=="function"||_at=="unknown"){xhr.abort();}var err=new Error("xhr cancelled");err.dojoType="cancel";return err;};var _46e=function(dfd){return _d._contentHandlers[dfd.ioArgs.handleAs](dfd.ioArgs.xhr);};var _470=function(_471,dfd){console.debug(_471);return _471;};var _473=function(args){var dfd=_d._ioSetArgs(args,_469,_46e,_470);dfd.ioArgs.xhr=_d._xhrObj(dfd.ioArgs.args);return dfd;};var _476=null;var _477=[];var _478=function(){var now=(new Date()).getTime();if(!_d._blockAsync){for(var i=0,tif;i<_477.length&&(tif=_477[i]);i++){var dfd=tif.dfd;try{if(!dfd||dfd.canceled||!tif.validCheck(dfd)){_477.splice(i--,1);}else{if(tif.ioCheck(dfd)){_477.splice(i--,1);tif.resHandle(dfd);}else{if(dfd.startTime){if(dfd.startTime+(dfd.ioArgs.args.timeout||0)<now){_477.splice(i--,1);var err=new Error("timeout exceeded");err.dojoType="timeout";dfd.errback(err);dfd.cancel();}}}}}catch(e){console.debug(e);dfd.errback(new Error("_watchInFlightError!"));}}}if(!_477.length){clearInterval(_476);_476=null;return;}};dojo._ioCancelAll=function(){try{_d.forEach(_477,function(i){i.dfd.cancel();});}catch(e){}};if(_d.isIE){_d.addOnUnload(_d._ioCancelAll);}_d._ioWatch=function(dfd,_480,_481,_482){if(dfd.ioArgs.args.timeout){dfd.startTime=(new Date()).getTime();}_477.push({dfd:dfd,validCheck:_480,ioCheck:_481,resHandle:_482});if(!_476){_476=setInterval(_478,50);}_478();};var _483="application/x-www-form-urlencoded";var _484=function(dfd){return dfd.ioArgs.xhr.readyState;};var _486=function(dfd){return 4==dfd.ioArgs.xhr.readyState;};var _488=function(dfd){var xhr=dfd.ioArgs.xhr;if(_d._isDocumentOk(xhr)){dfd.callback(dfd);}else{var err=new Error("Unable to load "+dfd.ioArgs.url+" status:"+xhr.status);err.status=xhr.status;err.responseText=xhr.responseText;dfd.errback(err);}};var _48c=function(type,dfd){var _48f=dfd.ioArgs;var args=_48f.args;var xhr=_48f.xhr;xhr.open(type,_48f.url,args.sync!==true,args.user||undefined,args.password||undefined);if(args.headers){for(var hdr in args.headers){if(hdr.toLowerCase()==="content-type"&&!args.contentType){args.contentType=args.headers[hdr];}else{xhr.setRequestHeader(hdr,args.headers[hdr]);}}}xhr.setRequestHeader("Content-Type",args.contentType||_483);if(!args.headers||!args.headers["X-Requested-With"]){xhr.setRequestHeader("X-Requested-With","XMLHttpRequest");}try{xhr.send(_48f.query);}catch(e){dfd.cancel();}_d._ioWatch(dfd,_484,_486,_488);xhr=null;return dfd;};dojo._ioAddQueryToUrl=function(_493){if(_493.query.length){_493.url+=(_493.url.indexOf("?")==-1?"?":"&")+_493.query;_493.query=null;}};dojo.xhr=function(_494,args,_496){var dfd=_473(args);if(!_496){_d._ioAddQueryToUrl(dfd.ioArgs);}return _48c(_494,dfd);};dojo.xhrGet=function(args){return _d.xhr("GET",args);};dojo.xhrPost=function(args){return _d.xhr("POST",args,true);};dojo.rawXhrPost=function(args){var dfd=_473(args);dfd.ioArgs.query=args.postData;return _48c("POST",dfd);};dojo.xhrPut=function(args){return _d.xhr("PUT",args,true);};dojo.rawXhrPut=function(args){var dfd=_473(args);var _49f=dfd.ioArgs;if(args.putData){_49f.query=args.putData;args.putData=null;}return _48c("PUT",dfd);};dojo.xhrDelete=function(args){return _d.xhr("DELETE",args);};})();}if(!dojo._hasResource["dojo._base.fx"]){dojo._hasResource["dojo._base.fx"]=true;dojo.provide("dojo._base.fx");(function(){var d=dojo;dojo._Line=function(_4a2,end){this.start=_4a2;this.end=end;this.getValue=function(n){return ((this.end-this.start)*n)+this.start;};};d.declare("dojo._Animation",null,{constructor:function(args){d.mixin(this,args);if(d.isArray(this.curve)){this.curve=new d._Line(this.curve[0],this.curve[1]);}},duration:350,repeat:0,rate:10,_percent:0,_startRepeatCount:0,_fire:function(evt,args){try{if(this[evt]){this[evt].apply(this,args||[]);}}catch(e){console.error("exception in animation handler for:",evt);console.error(e);}return this;},play:function(_4a8,_4a9){var _t=this;if(_4a9){_t._stopTimer();_t._active=_t._paused=false;_t._percent=0;}else{if(_t._active&&!_t._paused){return _t;}}_t._fire("beforeBegin");var de=_4a8||_t.delay;var _p=dojo.hitch(_t,"_play",_4a9);if(de>0){setTimeout(_p,de);return _t;}_p();return _t;},_play:function(_4ad){var _t=this;_t._startTime=new Date().valueOf();if(_t._paused){_t._startTime-=_t.duration*_t._percent;}_t._endTime=_t._startTime+_t.duration;_t._active=true;_t._paused=false;var _4af=_t.curve.getValue(_t._percent);if(!_t._percent){if(!_t._startRepeatCount){_t._startRepeatCount=_t.repeat;}_t._fire("onBegin",[_4af]);}_t._fire("onPlay",[_4af]);_t._cycle();return _t;},pause:function(){this._stopTimer();if(!this._active){return this;}this._paused=true;this._fire("onPause",[this.curve.getValue(this._percent)]);return this;},gotoPercent:function(_4b0,_4b1){this._stopTimer();this._active=this._paused=true;this._percent=_4b0;if(_4b1){this.play();}return this;},stop:function(_4b2){if(!this._timer){return this;}this._stopTimer();if(_4b2){this._percent=1;}this._fire("onStop",[this.curve.getValue(this._percent)]);this._active=this._paused=false;return this;},status:function(){if(this._active){return this._paused?"paused":"playing";}return "stopped";},_cycle:function(){var _t=this;if(_t._active){var curr=new Date().valueOf();var step=(curr-_t._startTime)/(_t._endTime-_t._startTime);if(step>=1){step=1;}_t._percent=step;if(_t.easing){step=_t.easing(step);}_t._fire("onAnimate",[_t.curve.getValue(step)]);if(_t._percent<1){_t._startTimer();}else{_t._active=false;if(_t.repeat>0){_t.repeat--;_t.play(null,true);}else{if(_t.repeat==-1){_t.play(null,true);}else{if(_t._startRepeatCount){_t.repeat=_t._startRepeatCount;_t._startRepeatCount=0;}}}_t._percent=0;_t._fire("onEnd");_t._stopTimer();}}return _t;}});var ctr=0;var _4b7=[];var _4b8={run:function(){}};var _4b9=null;dojo._Animation.prototype._startTimer=function(){if(!this._timer){this._timer=d.connect(_4b8,"run",this,"_cycle");ctr++;}if(!_4b9){_4b9=setInterval(d.hitch(_4b8,"run"),this.rate);}};dojo._Animation.prototype._stopTimer=function(){if(this._timer){d.disconnect(this._timer);this._timer=null;ctr--;}if(ctr<=0){clearInterval(_4b9);_4b9=null;ctr=0;}};var _4ba=(d.isIE)?function(node){var ns=node.style;if(!ns.zoom.length&&d.style(node,"zoom")=="normal"){ns.zoom="1";}if(!ns.width.length&&d.style(node,"width")=="auto"){ns.width="auto";}}:function(){};dojo._fade=function(args){args.node=d.byId(args.node);var _4be=d.mixin({properties:{}},args);var _4bf=(_4be.properties.opacity={});_4bf.start=!("start" in _4be)?function(){return Number(d.style(_4be.node,"opacity"));}:_4be.start;_4bf.end=_4be.end;var anim=d.animateProperty(_4be);d.connect(anim,"beforeBegin",d.partial(_4ba,_4be.node));return anim;};dojo.fadeIn=function(args){return d._fade(d.mixin({end:1},args));};dojo.fadeOut=function(args){return d._fade(d.mixin({end:0},args));};dojo._defaultEasing=function(n){return 0.5+((Math.sin((n+1.5)*Math.PI))/2);};var _4c4=function(_4c5){this._properties=_4c5;for(var p in _4c5){var prop=_4c5[p];if(prop.start instanceof d.Color){prop.tempColor=new d.Color();}}this.getValue=function(r){var ret={};for(var p in this._properties){var prop=this._properties[p];var _4cc=prop.start;if(_4cc instanceof d.Color){ret[p]=d.blendColors(_4cc,prop.end,r,prop.tempColor).toCss();}else{if(!d.isArray(_4cc)){ret[p]=((prop.end-_4cc)*r)+_4cc+(p!="opacity"?prop.units||"px":"");}}}return ret;};};dojo.animateProperty=function(args){args.node=d.byId(args.node);if(!args.easing){args.easing=d._defaultEasing;}var anim=new d._Animation(args);d.connect(anim,"beforeBegin",anim,function(){var pm={};for(var p in this.properties){if(p=="width"||p=="height"){this.node.display="block";}var prop=this.properties[p];prop=pm[p]=d.mixin({},(d.isObject(prop)?prop:{end:prop}));if(d.isFunction(prop.start)){prop.start=prop.start();}if(d.isFunction(prop.end)){prop.end=prop.end();}var _4d2=(p.toLowerCase().indexOf("color")>=0);function getStyle(node,p){var v=({height:node.offsetHeight,width:node.offsetWidth})[p];if(v!==undefined){return v;}v=d.style(node,p);return (p=="opacity")?Number(v):(_4d2?v:parseFloat(v));};if(!("end" in prop)){prop.end=getStyle(this.node,p);}else{if(!("start" in prop)){prop.start=getStyle(this.node,p);}}if(_4d2){prop.start=new d.Color(prop.start);prop.end=new d.Color(prop.end);}else{prop.start=(p=="opacity")?Number(prop.start):parseFloat(prop.start);}}this.curve=new _4c4(pm);});d.connect(anim,"onAnimate",anim,function(_4d6){for(var s in _4d6){d.style(this.node,s,_4d6[s]);}});return anim;};dojo.anim=function(node,_4d9,_4da,_4db,_4dc,_4dd){return d.animateProperty({node:node,duration:_4da||d._Animation.prototype.duration,properties:_4d9,easing:_4db,onEnd:_4dc}).play(_4dd||0);};})();}if(!dojo._hasResource["dojo._base.browser"]){dojo._hasResource["dojo._base.browser"]=true;dojo.provide("dojo._base.browser");if(dojo.config.require){dojo.forEach(dojo.config.require,"dojo['require'](item);");}}if(dojo.config.afterOnLoad&&dojo.isBrowser){window.setTimeout(dojo._fakeLoadInit,1000);}})(); Copied: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js (from rev 1396, branches/vhffs-design/vhffs-panel/js/dojo/dojo.js) =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/dojo.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dojo/dojo.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,16 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + +/* + This is a compiled version of Dojo, built for deployment and not for + development. To get an editable version, please visit: + + http://dojotoolkit.org + + for documentation and information on getting the source. +*/ + +(function(){var _1=null;if((_1||(typeof djConfig!="undefined"&&djConfig.scopeMap))&&(typeof window!="undefined")){var _2="",_3="",_4="",_5={},_6={};_1=_1||djConfig.scopeMap;for(var i=0;i<_1.length;i++){var _8=_1[i];_2+="var "+_8[0]+" = {}; "+_8[1]+" = "+_8[0]+";"+_8[1]+"._scopeName = '"+_8[1]+"';";_3+=(i==0?"":",")+_8[0];_4+=(i==0?"":",")+_8[1];_5[_8[0]]=_8[1];_6[_8[1]]=_8[0];}eval(_2+"dojo._scopeArgs = ["+_4+"];");dojo._scopePrefixArgs=_3;dojo._scopePrefix="(function("+_3+"){";dojo._scopeSuffix="})("+_4+")";dojo._scopeMap=_5;dojo._scopeMapRev=_6;}(function(){if(typeof this["loadFirebugConsole"]=="function"){this["loadFirebugConsole"]();}else{this.console=this.console||{};var cn=["assert","count","debug","dir","dirxml","error","group","groupEnd","info","profile","profileEnd","time","timeEnd","trace","warn","log"];var i=0,tn;while((tn=cn[i++])){if(!console[tn]){(function(){var _c=tn+"";console[_c]=("log" in console)?function(){var a=Array.apply({},arguments);a.unshift(_c+":");console["log"](a.join(" "));}:function(){};})();}}}if(typeof dojo=="undefined"){this.dojo={_scopeName:"dojo",_scopePrefix:"",_scopePrefixArgs:"",_scopeSuffix:"",_scopeMap:{},_scopeMapRev:{}};}var d=dojo;if(typeof dijit=="undefined"){this.dijit={_scopeName:"dijit"};}if(typeof dojox=="undefined"){this.dojox={_scopeName:"dojox"};}if(!d._scopeArgs){d._scopeArgs=[dojo,dijit,dojox];}d.global=this;d.config={isDebug:false,debugAtAllCosts:false};if(typeof djConfig!="undefined"){for(var _f in djConfig){d.config[_f]=djConfig[_f];}}dojo.locale=d.config.locale;var rev="$Rev: 17468 $".match(/\d+/);dojo.version={major:1,minor:3,patch:1,flag:"",revision:rev?+rev[0]:NaN,toString:function(){with(d.version){return major+"."+minor+"."+patch+flag+" ("+revision+")";}}};if(typeof OpenAjax!="undefined"){OpenAjax.hub.registerLibrary(dojo._scopeName,"http://dojotoolkit.org",d.version.toString());}var _11={};dojo._mixin=function(obj,_13){for(var x in _13){if(_11[x]===undefined||_11[x]!=_13[x]){obj[x]=_13[x];}}if(d.isIE&&_13){var p=_13.toString;if(typeof p=="function"&&p!=obj.toString&&p!=_11.toString&&p!="\nfunction toString() {\n [native code]\n}\n"){obj.toString=_13.toString;}}return obj;};dojo.mixin=function(obj,_17){if(!obj){obj={};}for(var i=1,l=arguments.length;i<l;i++){d._mixin(obj,arguments[i]);}return obj;};dojo._getProp=function(_1a,_1b,_1c){var obj=_1c||d.global;for(var i=0,p;obj&&(p=_1a[i]);i++){if(i==0&&this._scopeMap[p]){p=this._scopeMap[p];}obj=(p in obj?obj[p]:(_1b?obj[p]={}:undefined));}return obj;};dojo.setObject=function(_20,_21,_22){var _23=_20.split("."),p=_23.pop(),obj=d._getProp(_23,true,_22);return obj&&p?(obj[p]=_21):undefined;};dojo.getObject=function(_26,_27,_28){return d._getProp(_26.split("."),_27,_28);};dojo.exists=function(_29,obj){return !!d.getObject(_29,false,obj);};dojo["eval"]=function(_2b){return d.global.eval?d.global.eval(_2b):eval(_2b);};d.deprecated=d.experimental=function(){};})();(function(){var d=dojo;d.mixin(d,{_loadedModules:{},_inFlightCount:0,_hasResource:{},_modulePrefixes:{dojo:{name:"dojo",value:"."},doh:{name:"doh",value:"../util/doh"},tests:{name:"tests",value:"tests"}},_moduleHasPrefix:function(_2d){var mp=this._modulePrefixes;return !!(mp[_2d]&&mp[_2d].value);},_getModulePrefix:function(_2f){var mp=this._modulePrefixes;if(this._moduleHasPrefix(_2f)){return mp[_2f].value;}return _2f;},_loadedUrls:[],_postLoad:false,_loaders:[],_unloaders:[],_loadNotifying:false});dojo._loadPath=function(_31,_32,cb){var uri=((_31.charAt(0)=="/"||_31.match(/^\w+:/))?"":this.baseUrl)+_31;try{return !_32?this._loadUri(uri,cb):this._loadUriAndCheck(uri,_32,cb);}catch(e){console.error(e);return false;}};dojo._loadUri=function(uri,cb){if(this._loadedUrls[uri]){return true;}var _37=this._getText(uri,true);if(!_37){return false;}this._loadedUrls[uri]=true;this._loadedUrls.push(uri);if(cb){_37="("+_37+")";}else{_37=this._scopePrefix+_37+this._scopeSuffix;}if(d.isMoz){_37+="\r\n//@ sourceURL="+uri;}var _38=d["eval"](_37);if(cb){cb(_38);}return true;};dojo._loadUriAndCheck=function(uri,_3a,cb){var ok=false;try{ok=this._loadUri(uri,cb);}catch(e){console.error("failed loading "+uri+" with error: "+e);}return !!(ok&&this._loadedModules[_3a]);};dojo.loaded=function(){this._loadNotifying=true;this._postLoad=true;var mll=d._loaders;this._loaders=[];for(var x=0;x<mll.length;x++){mll[x]();}this._loadNotifying=false;if(d._postLoad&&d._inFlightCount==0&&mll.length){d._callLoaded();}};dojo.unloaded=function(){var mll=d._unloaders;while(mll.length){(mll.pop())();}};d._onto=function(arr,obj,fn){if(!fn){arr.push(obj);}else{if(fn){var _43=(typeof fn=="string")?obj[fn]:fn;arr.push(function(){_43.call(obj);});}}};dojo.addOnLoad=function(obj,_45){d._onto(d._loaders,obj,_45);if(d._postLoad&&d._inFlightCount==0&&!d._loadNotifying){d._callLoaded();}};var dca=d.config.addOnLoad;if(dca){d.addOnLoad[(dca instanceof Array?"apply":"call")](d,dca);}dojo._modulesLoaded=function(){if(d._postLoad){return;}if(d._inFlightCount>0){console.warn("files still in flight!");return;}d._callLoaded();};dojo._callLoaded=function(){if(typeof setTimeout=="object"||(dojo.config.useXDomain&&d.isOpera)){if(dojo.isAIR){setTimeout(function(){dojo.loaded();},0);}else{setTimeout(dojo._scopeName+".loaded();",0);}}else{d.loaded();}};dojo._getModuleSymbols=function(_47){var _48=_47.split(".");for(var i=_48.length;i>0;i--){var _4a=_48.slice(0,i).join(".");if((i==1)&&!this._moduleHasPrefix(_4a)){_48[0]="../"+_48[0];}else{var _4b=this._getModulePrefix(_4a);if(_4b!=_4a){_48.splice(0,i,_4b);break;}}}return _48;};dojo._global_omit_module_check=false;dojo.loadInit=function(_4c){_4c();};dojo._loadModule=dojo.require=function(_4d,_4e){_4e=this._global_omit_module_check||_4e;var _4f=this._loadedModules[_4d];if(_4f){return _4f;}var _50=this._getModuleSymbols(_4d).join("/")+".js";var _51=(!_4e)?_4d:null;var ok=this._loadPath(_50,_51);if(!ok&&!_4e){throw new Error("Could not load '"+_4d+"'; last tried '"+_50+"'");}if(!_4e&&!this._isXDomain){_4f=this._loadedModules[_4d];if(!_4f){throw new Error("symbol '"+_4d+"' is not defined after loading '"+_50+"'");}}return _4f;};dojo.provide=function(_53){_53=_53+"";return (d._loadedModules[_53]=d.getObject(_53,true));};dojo.platformRequire=function(_54){var _55=_54.common||[];var _56=_55.concat(_54[d._name]||_54["default"]||[]);for(var x=0;x<_56.length;x++){var _58=_56[x];if(_58.constructor==Array){d._loadModule.apply(d,_58);}else{d._loadModule(_58);}}};dojo.requireIf=function(_59,_5a){if(_59===true){var _5b=[];for(var i=1;i<arguments.length;i++){_5b.push(arguments[i]);}d.require.apply(d,_5b);}};dojo.requireAfterIf=d.requireIf;dojo.registerModulePath=function(_5d,_5e){d._modulePrefixes[_5d]={name:_5d,value:_5e};};dojo.requireLocalization=function(_5f,_60,_61,_62){d.require("dojo.i18n");d.i18n._requireLocalization.apply(d.hostenv,arguments);};var ore=new RegExp("^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$");var ire=new RegExp("^((([^\\[:]+):)?([^@]+)@)?(\\[([^\\]]+)\\]|([^\\[:]*))(:([0-9]+))?$");dojo._Url=function(){var n=null;var _a=arguments;var uri=[_a[0]];for(var i=1;i<_a.length;i++){if(!_a[i]){continue;}var _69=new d._Url(_a[i]+"");var _6a=new d._Url(uri[0]+"");if(_69.path==""&&!_69.scheme&&!_69.authority&&!_69.query){if(_69.fragment!=n){_6a.fragment=_69.fragment;}_69=_6a;}else{if(!_69.scheme){_69.scheme=_6a.scheme;if(!_69.authority){_69.authority=_6a.authority;if(_69.path.charAt(0)!="/"){var _6b=_6a.path.substring(0,_6a.path.lastIndexOf("/")+1)+_69.path;var _6c=_6b.split("/");for(var j=0;j<_6c.length;j++){if(_6c[j]=="."){if(j==_6c.length-1){_6c[j]="";}else{_6c.splice(j,1);j--;}}else{if(j>0&&!(j==1&&_6c[0]=="")&&_6c[j]==".."&&_6c[j-1]!=".."){if(j==(_6c.length-1)){_6c.splice(j,1);_6c[j-1]="";}else{_6c.splice(j-1,2);j-=2;}}}}_69.path=_6c.join("/");}}}}uri=[];if(_69.scheme){uri.push(_69.scheme,":");}if(_69.authority){uri.push("//",_69.authority);}uri.push(_69.path);if(_69.query){uri.push("?",_69.query);}if(_69.fragment){uri.push("#",_69.fragment);}}this.uri=uri.join("");var r=this.uri.match(ore);this.scheme=r[2]||(r[1]?"":n);this.authority=r[4]||(r[3]?"":n);this.path=r[5];this.query=r[7]||(r[6]?"":n);this.fragment=r[9]||(r[8]?"":n);if(this.authority!=n){r=this.authority.match(ire);this.user=r[3]||n;this.password=r[4]||n;this.host=r[6]||r[7];this.port=r[9]||n;}};dojo._Url.prototype.toString=function(){return this.uri;};dojo.moduleUrl=function(_6f,url){var loc=d._getModuleSymbols(_6f).join("/");if(!loc){return null;}if(loc.lastIndexOf("/")!=loc.length-1){loc+="/";}var _72=loc.indexOf(":");if(loc.charAt(0)!="/"&&(_72==-1||_72>loc.indexOf("/"))){loc=d.baseUrl+loc;}return new d._Url(loc,url);};})();if(typeof window!="undefined"){dojo.isBrowser=true;dojo._name="browser";(function(){var d=dojo;if(document&&document.getElementsByTagName){var _74=document.getElementsByTagName("script");var _75=/dojo(\.xd)?\.js(\W|$)/i;for(var i=0;i<_74.length;i++){var src=_74[i].getAttribute("src");if(!src){continue;}var m=src.match(_75);if(m){if(!d.config.baseUrl){d.config.baseUrl=src.substring(0,m.index);}var cfg=_74[i].getAttribute("djConfig");if(cfg){var _7a=eval("({ "+cfg+" })");for(var x in _7a){dojo.config[x]=_7a[x];}}break;}}}d.baseUrl=d.config.baseUrl;var n=navigator;var dua=n.userAgent,dav=n.appVersion,tv=parseFloat(dav);if(dua.indexOf("Opera")>=0){d.isOpera=tv;}if(dua.indexOf("AdobeAIR")>=0){d.isAIR=1;}d.isKhtml=(dav.indexOf("Konqueror")>=0)?tv:0;d.isWebKit=parseFloat(dua.split("WebKit/")[1])||undefined;d.isChrome=parseFloat(dua.split("Chrome/")[1])||undefined;var _80=Math.max(dav.indexOf("WebKit"),dav.indexOf("Safari"),0);if(_80&&!dojo.isChrome){d.isSafari=parseFloat(dav.split("Version/")[1]);if(!d.isSafari||parseFloat(dav.substr(_80+7))<=419.3){d.isSafari=2;}}if(dua.indexOf("Gecko")>=0&&!d.isKhtml&&!d.isWebKit){d.isMozilla=d.isMoz=tv;}if(d.isMoz){d.isFF=parseFloat(dua.split("Firefox/")[1]||dua.split("Minefield/")[1]||dua.split("Shiretoko/")[1])||undefined;}if(document.all&&!d.isOpera){d.isIE=parseFloat(dav.split("MSIE ")[1])||undefined;if(d.isIE>=8&&document.documentMode!=5){d.isIE=document.documentMode;}}if(dojo.isIE&&window.location.protocol==="file:"){dojo.config.ieForceActiveXXhr=true;}var cm=document.compatMode;d.isQuirks=cm=="BackCompat"||cm=="QuirksMode"||d.isIE<6;d.locale=dojo.config.locale||(d.isIE?n.userLanguage:n.language).toLowerCase();d._XMLHTTP_PROGIDS=["Msxml2.XMLHTTP","Microsoft.XMLHTTP","Msxml2.XMLHTTP.4.0"];d._xhrObj=function(){var _82,_83;if(!dojo.isIE||!dojo.config.ieForceActiveXXhr){try{_82=new XMLHttpRequest();}catch(e){}}if(!_82){for(var i=0;i<3;++i){var _85=d._XMLHTTP_PROGIDS[i];try{_82=new ActiveXObject(_85);}catch(e){_83=e;}if(_82){d._XMLHTTP_PROGIDS=[_85];break;}}}if(!_82){throw new Error("XMLHTTP not available: "+_83);}return _82;};d._isDocumentOk=function(_86){var _87=_86.status||0;return (_87>=200&&_87<300)||_87==304||_87==1223||(!_87&&(location.protocol=="file:"||location.protocol=="chrome:"));};var _88=window.location+"";var _89=document.getElementsByTagName("base");var _8a=(_89&&_89.length>0);d._getText=function(uri,_8c){var _8d=this._xhrObj();if(!_8a&&dojo._Url){uri=(new dojo._Url(_88,uri)).toString();}if(d.config.cacheBust){uri+="";uri+=(uri.indexOf("?")==-1?"?":"&")+String(d.config.cacheBust).replace(/\W+/g,"");}_8d.open("GET",uri,false);try{_8d.send(null);if(!d._isDocumentOk(_8d)){var err=Error("Unable to load "+uri+" status:"+_8d.status);err.status=_8d.status;err.responseText=_8d.responseText;throw err;}}catch(e){if(_8c){return null;}throw e;}return _8d.responseText;};var _w=window;var _90=function(_91,fp){var _93=_w[_91]||function(){};_w[_91]=function(){fp.apply(_w,arguments);_93.apply(_w,arguments);};};d._windowUnloaders=[];d.windowUnloaded=function(){var mll=d._windowUnloaders;while(mll.length){(mll.pop())();}};var _95=0;d.addOnWindowUnload=function(obj,_97){d._onto(d._windowUnloaders,obj,_97);if(!_95){_95=1;_90("onunload",d.windowUnloaded);}};var _98=0;d.addOnUnload=function(obj,_9a){d._onto(d._unloaders,obj,_9a);if(!_98){_98=1;_90("onbeforeunload",dojo.unloaded);}};})();dojo._initFired=false;dojo._loadInit=function(e){dojo._initFired=true;var _9c=e&&e.type?e.type.toLowerCase():"load";if(arguments.callee.initialized||(_9c!="domcontentloaded"&&_9c!="load")){return;}arguments.callee.initialized=true;if("_khtmlTimer" in dojo){clearInterval(dojo._khtmlTimer);delete dojo._khtmlTimer;}if(dojo._inFlightCount==0){dojo._modulesLoaded();}};if(!dojo.config.afterOnLoad){if(document.addEventListener){if(dojo.isWebKit>525||dojo.isOpera||dojo.isFF>=3||(dojo.isMoz&&dojo.config.enableMozDomContentLoaded===true)){document.addEventListener("DOMContentLoaded",dojo._loadInit,null);}window.addEventListener("load",dojo._loadInit,null);}if(dojo.isAIR){window.addEventListener("load",dojo._loadInit,null);}else{if((dojo.isWebKit<525)||dojo.isKhtml){dojo._khtmlTimer=setInterval(function(){if(/loaded|complete/.test(document.readyState)){dojo._loadInit();}},10);}}}if(dojo.isIE){if(!dojo.config.afterOnLoad){document.write("<scr"+"ipt defer src=\"//:\" "+"onreadystatechange=\"if(this.readyState=='complete'){"+dojo._scopeName+"._loadInit();}\">"+"</scr"+"ipt>");}try{document.namespaces.add("v","urn:schemas-microsoft-com:vml");document.createStyleSheet().addRule("v\\:*","behavior:url(#default#VML); display:inline-block");}catch(e){}}}(function(){var mp=dojo.config["modulePaths"];if(mp){for(var _9e in mp){dojo.registerModulePath(_9e,mp[_9e]);}}})();if(dojo.config.isDebug){dojo.require("dojo._firebug.firebug");}if(dojo.config.debugAtAllCosts){dojo.config.useXDomain=true;dojo.require("dojo._base._loader.loader_xd");dojo.require("dojo._base._loader.loader_debug");dojo.require("dojo.i18n");}if(!dojo._hasResource["dojo._base.lang"]){dojo._hasResource["dojo._base.lang"]=true;dojo.provide("dojo._base.lang");dojo.isString=function(it){return !!arguments.length&&it!=null&&(typeof it=="string"||it instanceof String);};dojo.isArray=function(it){return it&&(it instanceof Array||typeof it=="array");};dojo.isFunction=(function(){var _a1=function(it){var t=typeof it;return it&&(t=="function"||it instanceof Function);};return dojo.isSafari?function(it){if(typeof it=="function"&&it=="[object NodeList]"){return false;}return _a1(it);}:_a1;})();dojo.isObject=function(it){return it!==undefined&&(it===null||typeof it=="object"||dojo.isArray(it)||dojo.isFunction(it));};dojo.isArrayLike=function(it){var d=dojo;return it&&it!==undefined&&!d.isString(it)&&!d.isFunction(it)&&!(it.tagName&&it.tagName.toLowerCase()=="form")&&(d.isArray(it)||isFinite(it.length));};dojo.isAlien=function(it){return it&&!dojo.isFunction(it)&&/\{\s*\[native code\]\s*\}/.test(String(it));};dojo.extend=function(_a9,_aa){for(var i=1,l=arguments.length;i<l;i++){dojo._mixin(_a9.prototype,arguments[i]);}return _a9;};dojo._hitchArgs=function(_ad,_ae){var pre=dojo._toArray(arguments,2);var _b0=dojo.isString(_ae);return function(){var _b1=dojo._toArray(arguments);var f=_b0?(_ad||dojo.global)[_ae]:_ae;return f&&f.apply(_ad||this,pre.concat(_b1));};};dojo.hitch=function(_b3,_b4){if(arguments.length>2){return dojo._hitchArgs.apply(dojo,arguments);}if(!_b4){_b4=_b3;_b3=null;}if(dojo.isString(_b4)){_b3=_b3||dojo.global;if(!_b3[_b4]){throw (["dojo.hitch: scope[\"",_b4,"\"] is null (scope=\"",_b3,"\")"].join(""));}return function(){return _b3[_b4].apply(_b3,arguments||[]);};}return !_b3?_b4:function(){return _b4.apply(_b3,arguments||[]);};};dojo.delegate=dojo._delegate=(function(){function TMP(){};return function(obj,_b7){TMP.prototype=obj;var tmp=new TMP();if(_b7){dojo._mixin(tmp,_b7);}return tmp;};})();(function(){var _b9=function(obj,_bb,_bc){return (_bc||[]).concat(Array.prototype.slice.call(obj,_bb||0));};var _bd=function(obj,_bf,_c0){var arr=_c0||[];for(var x=_bf||0;x<obj.length;x++){arr.push(obj[x]);}return arr;};dojo._toArray=dojo.isIE?function(obj){return ((obj.item)?_bd:_b9).apply(this,arguments);}:_b9;})();dojo.partial=function(_c4){var arr=[null];return dojo.hitch.apply(dojo,arr.concat(dojo._toArray(arguments)));};dojo.clone=function(o){if(!o){return o;}if(dojo.isArray(o)){var r=[];for(var i=0;i<o.length;++i){r.push(dojo.clone(o[i]));}return r;}if(!dojo.isObject(o)){return o;}if(o.nodeType&&o.cloneNode){return o.cloneNode(true);}if(o instanceof Date){return new Date(o.getTime());}r=new o.constructor();for(i in o){if(!(i in r)||r[i]!=o[i]){r[i]=dojo.clone(o[i]);}}return r;};dojo.trim=String.prototype.trim?function(str){return str.trim();}:function(str){return str.replace(/^\s\s*/,"").replace(/\s\s*$/,"");};}if(!dojo._hasResource["dojo._base.declare"]){dojo._hasResource["dojo._base.declare"]=true;dojo.provide("dojo._base.declare");dojo.declare=function(_cb,_cc,_cd){var dd=arguments.callee,_cf;if(dojo.isArray(_cc)){_cf=_cc;_cc=_cf.shift();}if(_cf){dojo.forEach(_cf,function(m,i){if(!m){throw (_cb+": mixin #"+i+" is null");}_cc=dd._delegate(_cc,m);});}var _d2=dd._delegate(_cc);_cd=_cd||{};_d2.extend(_cd);dojo.extend(_d2,{declaredClass:_cb,_constructor:_cd.constructor});_d2.prototype.constructor=_d2;return dojo.setObject(_cb,_d2);};dojo.mixin(dojo.declare,{_delegate:function(_d3,_d4){var bp=(_d3||0).prototype,mp=(_d4||0).prototype,dd=dojo.declare;var _d8=dd._makeCtor();dojo.mixin(_d8,{superclass:bp,mixin:mp,extend:dd._extend});if(_d3){_d8.prototype=dojo._delegate(bp);}dojo.extend(_d8,dd._core,mp||0,{_constructor:null,preamble:null});_d8.prototype.constructor=_d8;_d8.prototype.declaredClass=(bp||0).declaredClass+"_"+(mp||0).declaredClass;return _d8;},_extend:function(_d9){var i,fn;for(i in _d9){if(dojo.isFunction(fn=_d9[i])&&!0[i]){fn.nom=i;fn.ctor=this;}}dojo.extend(this,_d9);},_makeCtor:function(){return function(){this._construct(arguments);};},_core:{_construct:function(_dc){var c=_dc.callee,s=c.superclass,ct=s&&s.constructor,m=c.mixin,mct=m&&m.constructor,a=_dc,ii,fn;if(a[0]){if(((fn=a[0].preamble))){a=fn.apply(this,a)||a;}}if((fn=c.prototype.preamble)){a=fn.apply(this,a)||a;}if(ct&&ct.apply){ct.apply(this,a);}if(mct&&mct.apply){mct.apply(this,a);}if((ii=c.prototype._constructor)){ii.apply(this,_dc);}if(this.constructor.prototype==c.prototype&&(ct=this.postscript)){ct.apply(this,_dc);}},_findMixin:function(_e5){var c=this.constructor,p,m;while(c){p=c.superclass;m=c.mixin;if(m==_e5||(m instanceof _e5.constructor)){return p;}if(m&&m._findMixin&&(m=m._findMixin(_e5))){return m;}c=p&&p.constructor;}},_findMethod:function(_e9,_ea,_eb,has){var p=_eb,c,m,f;do{c=p.constructor;m=c.mixin;if(m&&(m=this._findMethod(_e9,_ea,m,has))){return m;}if((f=p[_e9])&&(has==(f==_ea))){return p;}p=c.superclass;}while(p);return !has&&(p=this._findMixin(_eb))&&this._findMethod(_e9,_ea,p,has);},inherited:function(_f1,_f2,_f3){var a=arguments;if(!dojo.isString(a[0])){_f3=_f2;_f2=_f1;_f1=_f2.callee.nom;}a=_f3||_f2;var c=_f2.callee,p=this.constructor.prototype,fn,mp;if(this[_f1]!=c||p[_f1]==c){mp=(c.ctor||0).superclass||this._findMethod(_f1,c,p,true);if(!mp){throw (this.declaredClass+": inherited method \""+_f1+"\" mismatch");}p=this._findMethod(_f1,c,mp,false);}fn=p&&p[_f1];if(!fn){throw (mp.declaredClass+": inherited method \""+_f1+"\" not found");}return fn.apply(this,a);}}});}if(!dojo._hasResource["dojo._base.connect"]){dojo._hasResource["dojo._base.connect"]=true;dojo.provide("dojo._base.connect");dojo._listener={getDispatcher:function(){return function(){var ap=Array.prototype,c=arguments.callee,ls=c._listeners,t=c.target;var r=t&&t.apply(this,arguments);var lls;lls=[].concat(ls);for(var i in lls){if(!(i in ap)){lls[i].apply(this,arguments);}}return r;};},add:function(_100,_101,_102){_100=_100||dojo.global;var f=_100[_101];if(!f||!f._listeners){var d=dojo._listener.getDispatcher();d.target=f;d._listeners=[];f=_100[_101]=d;}return f._listeners.push(_102);},remove:function(_105,_106,_107){var f=(_105||dojo.global)[_106];if(f&&f._listeners&&_107--){delete f._listeners[_107];}}};dojo.connect=function(obj,_10a,_10b,_10c,_10d){var a=arguments,args=[],i=0;args.push(dojo.isString(a[0])?null:a[i++],a[i++]);var a1=a[i+1];args.push(dojo.isString(a1)||dojo.isFunction(a1)?a[i++]:null,a[i++]);for(var l=a.length;i<l;i++){args.push(a[i]);}return dojo._connect.apply(this,args);};dojo._connect=function(obj,_113,_114,_115){var l=dojo._listener,h=l.add(obj,_113,dojo.hitch(_114,_115));return [obj,_113,h,l];};dojo.disconnect=function(_118){if(_118&&_118[0]!==undefined){dojo._disconnect.apply(this,_118);delete _118[0];}};dojo._disconnect=function(obj,_11a,_11b,_11c){_11c.remove(obj,_11a,_11b);};dojo._topics={};dojo.subscribe=function(_11d,_11e,_11f){return [_11d,dojo._listener.add(dojo._topics,_11d,dojo.hitch(_11e,_11f))];};dojo.unsubscribe=function(_120){if(_120){dojo._listener.remove(dojo._topics,_120[0],_120[1]);}};dojo.publish=function(_121,args){var f=dojo._topics[_121];if(f){f.apply(this,args||[]);}};dojo.connectPublisher=function(_124,obj,_126){var pf=function(){dojo.publish(_124,arguments);};return (_126)?dojo.connect(obj,_126,pf):dojo.connect(obj,pf);};}if(!dojo._hasResource["dojo._base.Deferred"]){dojo._hasResource["dojo._base.Deferred"]=true;dojo.provide("dojo._base.Deferred");dojo.Deferred=function(_128){this.chain=[];this.id=this._nextId();this.fired=-1;this.paused=0;this.results=[null,null];this.canceller=_128;this.silentlyCancelled=false;};dojo.extend(dojo.Deferred,{_nextId:(function(){var n=1;return function(){return n++;};})(),cancel:function(){var err;if(this.fired==-1){if(this.canceller){err=this.canceller(this);}else{this.silentlyCancelled=true;}if(this.fired==-1){if(!(err instanceof Error)){var res=err;var msg="Deferred Cancelled";if(err&&err.toString){msg+=": "+err.toString();}err=new Error(msg);err.dojoType="cancel";err.cancelResult=res;}this.errback(err);}}else{if((this.fired==0)&&(this.results[0] instanceof dojo.Deferred)){this.results[0].cancel();}}},_resback:function(res){this.fired=((res instanceof Error)?1:0);this.results[this.fired]=res;this._fire();},_check:function(){if(this.fired!=-1){if(!this.silentlyCancelled){throw new Error("already called!");}this.silentlyCancelled=false;return;}},callback:function(res){this._check();this._resback(res);},errback:function(res){this._check();if(!(res instanceof Error)){res=new Error(res);}this._resback(res);},addBoth:function(cb,cbfn){var _132=dojo.hitch.apply(dojo,arguments);return this.addCallbacks(_132,_132);},addCallback:function(cb,cbfn){return this.addCallbacks(dojo.hitch.apply(dojo,arguments));},addErrback:function(cb,cbfn){return this.addCallbacks(null,dojo.hitch.apply(dojo,arguments));},addCallbacks:function(cb,eb){this.chain.push([cb,eb]);if(this.fired>=0){this._fire();}return this;},_fire:function(){var _139=this.chain;var _13a=this.fired;var res=this.results[_13a];var self=this;var cb=null;while((_139.length>0)&&(this.paused==0)){var f=_139.shift()[_13a];if(!f){continue;}var func=function(){var ret=f(res);if(typeof ret!="undefined"){res=ret;}_13a=((res instanceof Error)?1:0);if(res instanceof dojo.Deferred){cb=function(res){self._resback(res);self.paused--;if((self.paused==0)&&(self.fired>=0)){self._fire();}};this.paused++;}};if(dojo.config.debugAtAllCosts){func.call(this);}else{try{func.call(this);}catch(err){_13a=1;res=err;}}}this.fired=_13a;this.results[_13a]=res;if((cb)&&(this.paused)){res.addBoth(cb);}}});}if(!dojo._hasResource["dojo._base.json"]){dojo._hasResource["dojo._base.json"]=true;dojo.provide("dojo._base.json");dojo.fromJson=function(json){return eval("("+json+")");};dojo._escapeString=function(str){return ("\""+str.replace(/(["\\])/g,"\\$1")+"\"").replace(/[\f]/g,"\\f").replace(/[\b]/g,"\\b").replace(/[\n]/g,"\\n").replace(/[\t]/g,"\\t").replace(/[\r]/g,"\\r");};dojo.toJsonIndentStr="\t";dojo.toJson=function(it,_145,_146){if(it===undefined){return "undefined";}var _147=typeof it;if(_147=="number"||_147=="boolean"){return it+"";}if(it===null){return "null";}if(dojo.isString(it)){return dojo._escapeString(it);}var _148=arguments.callee;var _149;_146=_146||"";var _14a=_145?_146+dojo.toJsonIndentStr:"";var tf=it.__json__||it.json;if(dojo.isFunction(tf)){_149=tf.call(it);if(it!==_149){return _148(_149,_145,_14a);}}if(it.nodeType&&it.cloneNode){throw new Error("Can't serialize DOM nodes");}var sep=_145?" ":"";var _14d=_145?"\n":"";if(dojo.isArray(it)){var res=dojo.map(it,function(obj){var val=_148(obj,_145,_14a);if(typeof val!="string"){val="undefined";}return _14d+_14a+val;});return "["+res.join(","+sep)+_14d+_146+"]";}if(_147=="function"){return null;}var _151=[],key;for(key in it){var _153,val;if(typeof key=="number"){_153="\""+key+"\"";}else{if(typeof key=="string"){_153=dojo._escapeString(key);}else{continue;}}val=_148(it[key],_145,_14a);if(typeof val!="string"){continue;}_151.push(_14d+_14a+_153+":"+sep+val);}return "{"+_151.join(","+sep)+_14d+_146+"}";};}if(!dojo._hasResource["dojo._base.array"]){dojo._hasResource["dojo._base.array"]=true;dojo.provide("dojo._base.array");(function(){var _155=function(arr,obj,cb){return [dojo.isString(arr)?arr.split(""):arr,obj||dojo.global,dojo.isString(cb)?new Function("item","index","array",cb):cb];};dojo.mixin(dojo,{indexOf:function(_159,_15a,_15b,_15c){var step=1,end=_159.length||0,i=0;if(_15c){i=end-1;step=end=-1;}if(_15b!=undefined){i=_15b;}if((_15c&&i>end)||i<end){for(;i!=end;i+=step){if(_159[i]==_15a){return i;}}}return -1;},lastIndexOf:function(_15f,_160,_161){return dojo.indexOf(_15f,_160,_161,true);},forEach:function(arr,_163,_164){if(!arr||!arr.length){return;}var _p=_155(arr,_164,_163);arr=_p[0];for(var i=0,l=arr.length;i<l;++i){_p[2].call(_p[1],arr[i],i,arr);}},_everyOrSome:function(_168,arr,_16a,_16b){var _p=_155(arr,_16b,_16a);arr=_p[0];for(var i=0,l=arr.length;i<l;++i){var _16f=!!_p[2].call(_p[1],arr[i],i,arr);if(_168^_16f){return _16f;}}return _168;},every:function(arr,_171,_172){return this._everyOrSome(true,arr,_171,_172);},some:function(arr,_174,_175){return this._everyOrSome(false,arr,_174,_175);},map:function(arr,_177,_178){var _p=_155(arr,_178,_177);arr=_p[0];var _17a=(arguments[3]?(new arguments[3]()):[]);for(var i=0,l=arr.length;i<l;++i){_17a.push(_p[2].call(_p[1],arr[i],i,arr));}return _17a;},filter:function(arr,_17e,_17f){var _p=_155(arr,_17f,_17e);arr=_p[0];var _181=[];for(var i=0,l=arr.length;i<l;++i){if(_p[2].call(_p[1],arr[i],i,arr)){_181.push(arr[i]);}}return _181;}});})();}if(!dojo._hasResource["dojo._base.Color"]){dojo._hasResource["dojo._base.Color"]=true;dojo.provide("dojo._base.Color");(function(){var d=dojo;dojo.Color=function(_185){if(_185){this.setColor(_185);}};dojo.Color.named={black:[0,0,0],silver:[192,192,192],gray:[128,128,128],white:[255,255,255],maroon:[128,0,0],red:[255,0,0],purple:[128,0,128],fuchsia:[255,0,255],green:[0,128,0],lime:[0,255,0],olive:[128,128,0],yellow:[255,255,0],navy:[0,0,128],blue:[0,0,255],teal:[0,128,128],aqua:[0,255,255]};dojo.extend(dojo.Color,{r:255,g:255,b:255,a:1,_set:function(r,g,b,a){var t=this;t.r=r;t.g=g;t.b=b;t.a=a;},setColor:function(_18b){if(d.isString(_18b)){d.colorFromString(_18b,this);}else{if(d.isArray(_18b)){d.colorFromArray(_18b,this);}else{this._set(_18b.r,_18b.g,_18b.b,_18b.a);if(!(_18b instanceof d.Color)){this.sanitize();}}}return this;},sanitize:function(){return this;},toRgb:function(){var t=this;return [t.r,t.g,t.b];},toRgba:function(){var t=this;return [t.r,t.g,t.b,t.a];},toHex:function(){var arr=d.map(["r","g","b"],function(x){var s=this[x].toString(16);return s.length<2?"0"+s:s;},this);return "#"+arr.join("");},toCss:function(_191){var t=this,rgb=t.r+", "+t.g+", "+t.b;return (_191?"rgba("+rgb+", "+t.a:"rgb("+rgb)+")";},toString:function(){return this.toCss(true);}});dojo.blendColors=function(_194,end,_196,obj){var t=obj||new d.Color();d.forEach(["r","g","b","a"],function(x){t[x]=_194[x]+(end[x]-_194[x])*_196;if(x!="a"){t[x]=Math.round(t[x]);}});return t.sanitize();};dojo.colorFromRgb=function(_19a,obj){var m=_19a.toLowerCase().match(/^rgba?\(([\s\.,0-9]+)\)/);return m&&dojo.colorFromArray(m[1].split(/\s*,\s*/),obj);};dojo.colorFromHex=function(_19d,obj){var t=obj||new d.Color(),bits=(_19d.length==4)?4:8,mask=(1<<bits)-1;_19d=Number("0x"+_19d.substr(1));if(isNaN(_19d)){return null;}d.forEach(["b","g","r"],function(x){var c=_19d&mask;_19d>>=bits;t[x]=bits==4?17*c:c;});t.a=1;return t;};dojo.colorFromArray=function(a,obj){var t=obj||new d.Color();t._set(Number(a[0]),Number(a[1]),Number(a[2]),Number(a[3]));if(isNaN(t.a)){t.a=1;}return t.sanitize();};dojo.colorFromString=function(str,obj){var a=d.Color.named[str];return a&&d.colorFromArray(a,obj)||d.colorFromRgb(str,obj)||d.colorFromHex(str,obj);};})();}if(!dojo._hasResource["dojo._base"]){dojo._hasResource["dojo._base"]=true;dojo.provide("dojo._base");}if(!dojo._hasResource["dojo._base.window"]){dojo._hasResource["dojo._base.window"]=true;dojo.provide("dojo._base.window");dojo.doc=window["document"]||null;dojo.body=function(){return dojo.doc.body||dojo.doc.getElementsByTagName("body")[0];};dojo.setContext=function(_1aa,_1ab){dojo.global=_1aa;dojo.doc=_1ab;};dojo.withGlobal=function(_1ac,_1ad,_1ae,_1af){var _1b0=dojo.global;try{dojo.global=_1ac;return dojo.withDoc.call(null,_1ac.document,_1ad,_1ae,_1af);}finally{dojo.global=_1b0;}};dojo.withDoc=function(_1b1,_1b2,_1b3,_1b4){var _1b5=dojo.doc,_1b6=dojo._bodyLtr;try{dojo.doc=_1b1;delete dojo._bodyLtr;if(_1b3&&dojo.isString(_1b2)){_1b2=_1b3[_1b2];}return _1b2.apply(_1b3,_1b4||[]);}finally{dojo.doc=_1b5;if(_1b6!==undefined){dojo._bodyLtr=_1b6;}}};}if(!dojo._hasResource["dojo._base.event"]){dojo._hasResource["dojo._base.event"]=true;dojo.provide("dojo._base.event");(function(){var del=(dojo._event_listener={add:function(node,name,fp){if(!node){return;}name=del._normalizeEventName(name);fp=del._fixCallback(name,fp);var _1bb=name;if(!dojo.isIE&&(name=="mouseenter"||name=="mouseleave")){var ofp=fp;name=(name=="mouseenter")?"mouseover":"mouseout";fp=function(e){if(dojo.isFF<=2){try{e.relatedTarget.tagName;}catch(e2){return;}}if(!dojo.isDescendant(e.relatedTarget,node)){return ofp.call(this,e);}};}node.addEventListener(name,fp,false);return fp;},remove:function(node,_1bf,_1c0){if(node){_1bf=del._normalizeEventName(_1bf);if(!dojo.isIE&&(_1bf=="mouseenter"||_1bf=="mouseleave")){_1bf=(_1bf=="mouseenter")?"mouseover":"mouseout";}node.removeEventListener(_1bf,_1c0,false);}},_normalizeEventName:function(name){return name.slice(0,2)=="on"?name.slice(2):name;},_fixCallback:function(name,fp){return name!="keypress"?fp:function(e){return fp.call(this,del._fixEvent(e,this));};},_fixEvent:function(evt,_1c6){switch(evt.type){case "keypress":del._setKeyChar(evt);break;}return evt;},_setKeyChar:function(evt){evt.keyChar=evt.charCode?String.fromCharCode(evt.charCode):"";evt.charOrCode=evt.keyChar||evt.keyCode;},_punctMap:{106:42,111:47,186:59,187:43,188:44,189:45,190:46,191:47,192:96,219:91,220:92,221:93,222:39}});dojo.fixEvent=function(evt,_1c9){return del._fixEvent(evt,_1c9);};dojo.stopEvent=function(evt){evt.preventDefault();evt.stopPropagation();};var _1cb=dojo._listener;dojo._connect=function(obj,_1cd,_1ce,_1cf,_1d0){var _1d1=obj&&(obj.nodeType||obj.attachEvent||obj.addEventListener);var lid=_1d1?(_1d0?2:1):0,l=[dojo._listener,del,_1cb][lid];var h=l.add(obj,_1cd,dojo.hitch(_1ce,_1cf));return [obj,_1cd,h,lid];};dojo._disconnect=function(obj,_1d6,_1d7,_1d8){([dojo._listener,del,_1cb][_1d8]).remove(obj,_1d6,_1d7);};dojo.keys={BACKSPACE:8,TAB:9,CLEAR:12,ENTER:13,SHIFT:16,CTRL:17,ALT:18,PAUSE:19,CAPS_LOCK:20,ESCAPE:27,SPACE:32,PAGE_UP:33,PAGE_DOWN:34,END:35,HOME:36,LEFT_ARROW:37,UP_ARROW:38,RIGHT_ARROW:39,DOWN_ARROW:40,INSERT:45,DELETE:46,HELP:47,LEFT_WINDOW:91,RIGHT_WINDOW:92,SELECT:93,NUMPAD_0:96,NUMPAD_1:97,NUMPAD_2:98,NUMPAD_3:99,NUMPAD_4:100,NUMPAD_5:101,NUMPAD_6:102,NUMPAD_7:103,NUMPAD_8:104,NUMPAD_9:105,NUMPAD_MULTIPLY:106,NUMPAD_PLUS:107,NUMPAD_ENTER:108,NUMPAD_MINUS:109,NUMPAD_PERIOD:110,NUMPAD_DIVIDE:111,F1:112,F2:113,F3:114,F4:115,F5:116,F6:117,F7:118,F8:119,F9:120,F10:121,F11:122,F12:123,F13:124,F14:125,F15:126,NUM_LOCK:144,SCROLL_LOCK:145};if(dojo.isIE){var _1d9=function(e,code){try{return (e.keyCode=code);}catch(e){return 0;}};var iel=dojo._listener;var _1dd=(dojo._ieListenersName="_"+dojo._scopeName+"_listeners");if(!dojo.config._allow_leaks){_1cb=iel=dojo._ie_listener={handlers:[],add:function(_1de,_1df,_1e0){_1de=_1de||dojo.global;var f=_1de[_1df];if(!f||!f[_1dd]){var d=dojo._getIeDispatcher();d.target=f&&(ieh.push(f)-1);d[_1dd]=[];f=_1de[_1df]=d;}return f[_1dd].push(ieh.push(_1e0)-1);},remove:function(_1e4,_1e5,_1e6){var f=(_1e4||dojo.global)[_1e5],l=f&&f[_1dd];if(f&&l&&_1e6--){delete ieh[l[_1e6]];delete l[_1e6];}}};var ieh=iel.handlers;}dojo.mixin(del,{add:function(node,_1ea,fp){if(!node){return;}_1ea=del._normalizeEventName(_1ea);if(_1ea=="onkeypress"){var kd=node.onkeydown;if(!kd||!kd[_1dd]||!kd._stealthKeydownHandle){var h=del.add(node,"onkeydown",del._stealthKeyDown);kd=node.onkeydown;kd._stealthKeydownHandle=h;kd._stealthKeydownRefs=1;}else{kd._stealthKeydownRefs++;}}return iel.add(node,_1ea,del._fixCallback(fp));},remove:function(node,_1ef,_1f0){_1ef=del._normalizeEventName(_1ef);iel.remove(node,_1ef,_1f0);if(_1ef=="onkeypress"){var kd=node.onkeydown;if(--kd._stealthKeydownRefs<=0){iel.remove(node,"onkeydown",kd._stealthKeydownHandle);delete kd._stealthKeydownHandle;}}},_normalizeEventName:function(_1f2){return _1f2.slice(0,2)!="on"?"on"+_1f2:_1f2;},_nop:function(){},_fixEvent:function(evt,_1f4){if(!evt){var w=_1f4&&(_1f4.ownerDocument||_1f4.document||_1f4).parentWindow||window;evt=w.event;}if(!evt){return (evt);}evt.target=evt.srcElement;evt.currentTarget=(_1f4||evt.srcElement);evt.layerX=evt.offsetX;evt.layerY=evt.offsetY;var se=evt.srcElement,doc=(se&&se.ownerDocument)||document;var _1f8=((dojo.isIE<6)||(doc["compatMode"]=="BackCompat"))?doc.body:doc.documentElement;var _1f9=dojo._getIeDocumentElementOffset();evt.pageX=evt.clientX+dojo._fixIeBiDiScrollLeft(_1f8.scrollLeft||0)-_1f9.x;evt.pageY=evt.clientY+(_1f8.scrollTop||0)-_1f9.y;if(evt.type=="mouseover"){evt.relatedTarget=evt.fromElement;}if(evt.type=="mouseout"){evt.relatedTarget=evt.toElement;}evt.stopPropagation=del._stopPropagation;evt.preventDefault=del._preventDefault;return del._fixKeys(evt);},_fixKeys:function(evt){switch(evt.type){case "keypress":var c=("charCode" in evt?evt.charCode:evt.keyCode);if(c==10){c=0;evt.keyCode=13;}else{if(c==13||c==27){c=0;}else{if(c==3){c=99;}}}evt.charCode=c;del._setKeyChar(evt);break;}return evt;},_stealthKeyDown:function(evt){var kp=evt.currentTarget.onkeypress;if(!kp||!kp[_1dd]){return;}var k=evt.keyCode;var _1ff=k!=13&&k!=32&&k!=27&&(k<48||k>90)&&(k<96||k>111)&&(k<186||k>192)&&(k<219||k>222);if(_1ff||evt.ctrlKey){var c=_1ff?0:k;if(evt.ctrlKey){if(k==3||k==13){return;}else{if(c>95&&c<106){c-=48;}else{if((!evt.shiftKey)&&(c>=65&&c<=90)){c+=32;}else{c=del._punctMap[c]||c;}}}}var faux=del._synthesizeEvent(evt,{type:"keypress",faux:true,charCode:c});kp.call(evt.currentTarget,faux);evt.cancelBubble=faux.cancelBubble;evt.returnValue=faux.returnValue;_1d9(evt,faux.keyCode);}},_stopPropagation:function(){this.cancelBubble=true;},_preventDefault:function(){this.bubbledKeyCode=this.keyCode;if(this.ctrlKey){_1d9(this,0);}this.returnValue=false;}});dojo.stopEvent=function(evt){evt=evt||window.event;del._stopPropagation.call(evt);del._preventDefault.call(evt);};}del._synthesizeEvent=function(evt,_204){var faux=dojo.mixin({},evt,_204);del._setKeyChar(faux);faux.preventDefault=function(){evt.preventDefault();};faux.stopPropagation=function(){evt.stopPropagation();};return faux;};if(dojo.isOpera){dojo.mixin(del,{_fixEvent:function(evt,_207){switch(evt.type){case "keypress":var c=evt.which;if(c==3){c=99;}c=c<41&&!evt.shiftKey?0:c;if(evt.ctrlKey&&!evt.shiftKey&&c>=65&&c<=90){c+=32;}return del._synthesizeEvent(evt,{charCode:c});}return evt;}});}if(dojo.isWebKit){del._add=del.add;del._remove=del.remove;dojo.mixin(del,{add:function(node,_20a,fp){if(!node){return;}var _20c=del._add(node,_20a,fp);if(del._normalizeEventName(_20a)=="keypress"){_20c._stealthKeyDownHandle=del._add(node,"keydown",function(evt){var k=evt.keyCode;var _20f=k!=13&&k!=32&&k!=27&&(k<48||k>90)&&(k<96||k>111)&&(k<186||k>192)&&(k<219||k>222);if(_20f||evt.ctrlKey){var c=_20f?0:k;if(evt.ctrlKey){if(k==3||k==13){return;}else{if(c>95&&c<106){c-=48;}else{if(!evt.shiftKey&&c>=65&&c<=90){c+=32;}else{c=del._punctMap[c]||c;}}}}var faux=del._synthesizeEvent(evt,{type:"keypress",faux:true,charCode:c});fp.call(evt.currentTarget,faux);}});}return _20c;},remove:function(node,_213,_214){if(node){if(_214._stealthKeyDownHandle){del._remove(node,"keydown",_214._stealthKeyDownHandle);}del._remove(node,_213,_214);}},_fixEvent:function(evt,_216){switch(evt.type){case "keypress":if(evt.faux){return evt;}var c=evt.charCode;c=c>=32?c:0;return del._synthesizeEvent(evt,{charCode:c,faux:true});}return evt;}});}})();if(dojo.isIE){dojo._ieDispatcher=function(args,_219){var ap=Array.prototype,h=dojo._ie_listener.handlers,c=args.callee,ls=c[dojo._ieListenersName],t=h[c.target];var r=t&&t.apply(_219,args);var lls=[].concat(ls);for(var i in lls){var f=h[lls[i]];if(!(i in ap)&&f){f.apply(_219,args);}}return r;};dojo._getIeDispatcher=function(){return new Function(dojo._scopeName+"._ieDispatcher(arguments, this)");};dojo._event_listener._fixCallback=function(fp){var f=dojo._event_listener._fixEvent;return function(e){return fp.call(this,f(e,this));};};}}if(!dojo._hasResource["dojo._base.html"]){dojo._hasResource["dojo._base.html"]=true;dojo.provide("dojo._base.html");try{document.execCommand("BackgroundImageCache",false,true);}catch(e){}if(dojo.isIE||dojo.isOpera){dojo.byId=function(id,doc){if(dojo.isString(id)){var _d=doc||dojo.doc;var te=_d.getElementById(id);if(te&&(te.attributes.id.value==id||te.id==id)){return te;}else{var eles=_d.all[id];if(!eles||eles.nodeName){eles=[eles];}var i=0;while((te=eles[i++])){if((te.attributes&&te.attributes.id&&te.attributes.id.value==id)||te.id==id){return te;}}}}else{return id;}};}else{dojo.byId=function(id,doc){return dojo.isString(id)?(doc||dojo.doc).getElementById(id):id;};}(function(){var d=dojo;var _22f=null;d.addOnWindowUnload(function(){_22f=null;});dojo._destroyElement=dojo.destroy=function(node){node=d.byId(node);try{if(!_22f||_22f.ownerDocument!=node.ownerDocument){_22f=node.ownerDocument.createElement("div");}_22f.appendChild(node.parentNode?node.parentNode.removeChild(node):node);_22f.innerHTML="";}catch(e){}};dojo.isDescendant=function(node,_232){try{node=d.byId(node);_232=d.byId(_232);while(node){if(node===_232){return true;}node=node.parentNode;}}catch(e){}return false;};dojo.setSelectable=function(node,_234){node=d.byId(node);if(d.isMozilla){node.style.MozUserSelect=_234?"":"none";}else{if(d.isKhtml||d.isWebKit){node.style.KhtmlUserSelect=_234?"auto":"none";}else{if(d.isIE){var v=(node.unselectable=_234?"":"on");d.query("*",node).forEach("item.unselectable = '"+v+"'");}}}};var _236=function(node,ref){var _239=ref.parentNode;if(_239){_239.insertBefore(node,ref);}};var _23a=function(node,ref){var _23d=ref.parentNode;if(_23d){if(_23d.lastChild==ref){_23d.appendChild(node);}else{_23d.insertBefore(node,ref.nextSibling);}}};dojo.place=function(node,_23f,_240){_23f=d.byId(_23f);if(d.isString(node)){node=node.charAt(0)=="<"?d._toDom(node,_23f.ownerDocument):d.byId(node);}if(typeof _240=="number"){var cn=_23f.childNodes;if(!cn.length||cn.length<=_240){_23f.appendChild(node);}else{_236(node,cn[_240<0?0:_240]);}}else{switch(_240){case "before":_236(node,_23f);break;case "after":_23a(node,_23f);break;case "replace":_23f.parentNode.replaceChild(node,_23f);break;case "only":d.empty(_23f);_23f.appendChild(node);break;case "first":if(_23f.firstChild){_236(node,_23f.firstChild);break;}default:_23f.appendChild(node);}}return node;};dojo.boxModel="content-box";if(d.isIE){var _dcm=document.compatMode;d.boxModel=_dcm=="BackCompat"||_dcm=="QuirksMode"||d.isIE<6?"border-box":"content-box";}var gcs;if(d.isWebKit){gcs=function(node){var s;if(node instanceof HTMLElement){var dv=node.ownerDocument.defaultView;s=dv.getComputedStyle(node,null);if(!s&&node.style){node.style.display="";s=dv.getComputedStyle(node,null);}}return s||{};};}else{if(d.isIE){gcs=function(node){return node.nodeType==1?node.currentStyle:{};};}else{gcs=function(node){return node instanceof HTMLElement?node.ownerDocument.defaultView.getComputedStyle(node,null):{};};}}dojo.getComputedStyle=gcs;if(!d.isIE){d._toPixelValue=function(_249,_24a){return parseFloat(_24a)||0;};}else{d._toPixelValue=function(_24b,_24c){if(!_24c){return 0;}if(_24c=="medium"){return 4;}if(_24c.slice&&_24c.slice(-2)=="px"){return parseFloat(_24c);}with(_24b){var _24d=style.left;var _24e=runtimeStyle.left;runtimeStyle.left=currentStyle.left;try{style.left=_24c;_24c=style.pixelLeft;}catch(e){_24c=0;}style.left=_24d;runtimeStyle.left=_24e;}return _24c;};}var px=d._toPixelValue;var astr="DXImageTransform.Microsoft.Alpha";var af=function(n,f){try{return n.filters.item(astr);}catch(e){return f?{}:null;}};dojo._getOpacity=d.isIE?function(node){try{return af(node).Opacity/100;}catch(e){return 1;}}:function(node){return gcs(node).opacity;};dojo._setOpacity=d.isIE?function(node,_257){var ov=_257*100;node.style.zoom=1;af(node,1).Enabled=!(_257==1);if(!af(node)){node.style.filter+=" progid:"+astr+"(Opacity="+ov+")";}else{af(node,1).Opacity=ov;}if(node.nodeName.toLowerCase()=="tr"){d.query("> td",node).forEach(function(i){d._setOpacity(i,_257);});}return _257;}:function(node,_25b){return node.style.opacity=_25b;};var _25c={left:true,top:true};var _25d=/margin|padding|width|height|max|min|offset/;var _25e=function(node,type,_261){type=type.toLowerCase();if(d.isIE){if(_261=="auto"){if(type=="height"){return node.offsetHeight;}if(type=="width"){return node.offsetWidth;}}if(type=="fontweight"){switch(_261){case 700:return "bold";case 400:default:return "normal";}}}if(!(type in _25c)){_25c[type]=_25d.test(type);}return _25c[type]?px(node,_261):_261;};var _262=d.isIE?"styleFloat":"cssFloat",_263={"cssFloat":_262,"styleFloat":_262,"float":_262};dojo.style=function(node,_265,_266){var n=d.byId(node),args=arguments.length,op=(_265=="opacity");_265=_263[_265]||_265;if(args==3){return op?d._setOpacity(n,_266):n.style[_265]=_266;}if(args==2&&op){return d._getOpacity(n);}var s=gcs(n);if(args==2&&!d.isString(_265)){for(var x in _265){d.style(node,x,_265[x]);}return s;}return (args==1)?s:_25e(n,_265,s[_265]||n.style[_265]);};dojo._getPadExtents=function(n,_26d){var s=_26d||gcs(n),l=px(n,s.paddingLeft),t=px(n,s.paddingTop);return {l:l,t:t,w:l+px(n,s.paddingRight),h:t+px(n,s.paddingBottom)};};dojo._getBorderExtents=function(n,_272){var ne="none",s=_272||gcs(n),bl=(s.borderLeftStyle!=ne?px(n,s.borderLeftWidth):0),bt=(s.borderTopStyle!=ne?px(n,s.borderTopWidth):0);return {l:bl,t:bt,w:bl+(s.borderRightStyle!=ne?px(n,s.borderRightWidth):0),h:bt+(s.borderBottomStyle!=ne?px(n,s.borderBottomWidth):0)};};dojo._getPadBorderExtents=function(n,_278){var s=_278||gcs(n),p=d._getPadExtents(n,s),b=d._getBorderExtents(n,s);return {l:p.l+b.l,t:p.t+b.t,w:p.w+b.w,h:p.h+b.h};};dojo._getMarginExtents=function(n,_27d){var s=_27d||gcs(n),l=px(n,s.marginLeft),t=px(n,s.marginTop),r=px(n,s.marginRight),b=px(n,s.marginBottom);if(d.isWebKit&&(s.position!="absolute")){r=l;}return {l:l,t:t,w:l+r,h:t+b};};dojo._getMarginBox=function(node,_284){var s=_284||gcs(node),me=d._getMarginExtents(node,s);var l=node.offsetLeft-me.l,t=node.offsetTop-me.t,p=node.parentNode;if(d.isMoz){var sl=parseFloat(s.left),st=parseFloat(s.top);if(!isNaN(sl)&&!isNaN(st)){l=sl,t=st;}else{if(p&&p.style){var pcs=gcs(p);if(pcs.overflow!="visible"){var be=d._getBorderExtents(p,pcs);l+=be.l,t+=be.t;}}}}else{if(d.isOpera||(d.isIE>7&&!d.isQuirks)){if(p){be=d._getBorderExtents(p);l-=be.l;t-=be.t;}}}return {l:l,t:t,w:node.offsetWidth+me.w,h:node.offsetHeight+me.h};};dojo._getContentBox=function(node,_28f){var s=_28f||gcs(node),pe=d._getPadExtents(node,s),be=d._getBorderExtents(node,s),w=node.clientWidth,h;if(!w){w=node.offsetWidth,h=node.offsetHeight;}else{h=node.clientHeight,be.w=be.h=0;}if(d.isOpera){pe.l+=be.l;pe.t+=be.t;}return {l:pe.l,t:pe.t,w:w-pe.w-be.w,h:h-pe.h-be.h};};dojo._getBorderBox=function(node,_296){var s=_296||gcs(node),pe=d._getPadExtents(node,s),cb=d._getContentBox(node,s);return {l:cb.l-pe.l,t:cb.t-pe.t,w:cb.w+pe.w,h:cb.h+pe.h};};dojo._setBox=function(node,l,t,w,h,u){u=u||"px";var s=node.style;if(!isNaN(l)){s.left=l+u;}if(!isNaN(t)){s.top=t+u;}if(w>=0){s.width=w+u;}if(h>=0){s.height=h+u;}};dojo._isButtonTag=function(node){return node.tagName=="BUTTON"||node.tagName=="INPUT"&&node.getAttribute("type").toUpperCase()=="BUTTON";};dojo._usesBorderBox=function(node){var n=node.tagName;return d.boxModel=="border-box"||n=="TABLE"||d._isButtonTag(node);};dojo._setContentSize=function(node,_2a5,_2a6,_2a7){if(d._usesBorderBox(node)){var pb=d._getPadBorderExtents(node,_2a7);if(_2a5>=0){_2a5+=pb.w;}if(_2a6>=0){_2a6+=pb.h;}}d._setBox(node,NaN,NaN,_2a5,_2a6);};dojo._setMarginBox=function(node,_2aa,_2ab,_2ac,_2ad,_2ae){var s=_2ae||gcs(node),bb=d._usesBorderBox(node),pb=bb?_2b2:d._getPadBorderExtents(node,s);if(d.isWebKit){if(d._isButtonTag(node)){var ns=node.style;if(_2ac>=0&&!ns.width){ns.width="4px";}if(_2ad>=0&&!ns.height){ns.height="4px";}}}var mb=d._getMarginExtents(node,s);if(_2ac>=0){_2ac=Math.max(_2ac-pb.w-mb.w,0);}if(_2ad>=0){_2ad=Math.max(_2ad-pb.h-mb.h,0);}d._setBox(node,_2aa,_2ab,_2ac,_2ad);};var _2b2={l:0,t:0,w:0,h:0};dojo.marginBox=function(node,box){var n=d.byId(node),s=gcs(n),b=box;return !b?d._getMarginBox(n,s):d._setMarginBox(n,b.l,b.t,b.w,b.h,s);};dojo.contentBox=function(node,box){var n=d.byId(node),s=gcs(n),b=box;return !b?d._getContentBox(n,s):d._setContentSize(n,b.w,b.h,s);};var _2bf=function(node,prop){if(!(node=(node||0).parentNode)){return 0;}var val,_2c3=0,_b=d.body();while(node&&node.style){if(gcs(node).position=="fixed"){return 0;}val=node[prop];if(val){_2c3+=val-0;if(node==_b){break;}}node=node.parentNode;}return _2c3;};dojo._docScroll=function(){var _b=d.body(),_w=d.global,de=d.doc.documentElement;return {y:(_w.pageYOffset||de.scrollTop||_b.scrollTop||0),x:(_w.pageXOffset||d._fixIeBiDiScrollLeft(de.scrollLeft)||_b.scrollLeft||0)};};dojo._isBodyLtr=function(){return ("_bodyLtr" in d)?d._bodyLtr:d._bodyLtr=gcs(d.body()).direction=="ltr";};dojo._getIeDocumentElementOffset=function(){var de=d.doc.documentElement;if(d.isIE<7){return {x:d._isBodyLtr()||window.parent==window?de.clientLeft:de.offsetWidth-de.clientWidth-de.clientLeft,y:de.clientTop};}else{if(d.isIE<8){return {x:de.getBoundingClientRect().left,y:de.getBoundingClientRect().top};}else{return {x:0,y:0};}}};dojo._fixIeBiDiScrollLeft=function(_2c9){var dd=d.doc;if(d.isIE<8&&!d._isBodyLtr()){var de=dd.compatMode=="BackCompat"?dd.body:dd.documentElement;return _2c9+de.clientWidth-de.scrollWidth;}return _2c9;};dojo._abs=function(node,_2cd){var db=d.body(),dh=d.body().parentNode,ret;if(node["getBoundingClientRect"]){var _2d1=node.getBoundingClientRect();ret={x:_2d1.left,y:_2d1.top};if(d.isFF>=3){var cs=gcs(dh);ret.x-=px(dh,cs.marginLeft)+px(dh,cs.borderLeftWidth);ret.y-=px(dh,cs.marginTop)+px(dh,cs.borderTopWidth);}if(d.isIE){var _2d3=d._getIeDocumentElementOffset();ret.x-=_2d3.x+(d.isQuirks?db.clientLeft:0);ret.y-=_2d3.y+(d.isQuirks?db.clientTop:0);}}else{ret={x:0,y:0};if(node["offsetParent"]){ret.x-=_2bf(node,"scrollLeft");ret.y-=_2bf(node,"scrollTop");var _2d4=node;do{var n=_2d4.offsetLeft,t=_2d4.offsetTop;ret.x+=isNaN(n)?0:n;ret.y+=isNaN(t)?0:t;cs=gcs(_2d4);if(_2d4!=node){if(d.isFF){ret.x+=2*px(_2d4,cs.borderLeftWidth);ret.y+=2*px(_2d4,cs.borderTopWidth);}else{ret.x+=px(_2d4,cs.borderLeftWidth);ret.y+=px(_2d4,cs.borderTopWidth);}}if(d.isFF&&cs.position=="static"){var _2d7=_2d4.parentNode;while(_2d7!=_2d4.offsetParent){var pcs=gcs(_2d7);if(pcs.position=="static"){ret.x+=px(_2d4,pcs.borderLeftWidth);ret.y+=px(_2d4,pcs.borderTopWidth);}_2d7=_2d7.parentNode;}}_2d4=_2d4.offsetParent;}while((_2d4!=dh)&&_2d4);}else{if(node.x&&node.y){ret.x+=isNaN(node.x)?0:node.x;ret.y+=isNaN(node.y)?0:node.y;}}}if(_2cd){var _2d9=d._docScroll();ret.x+=_2d9.x;ret.y+=_2d9.y;}return ret;};dojo.coords=function(node,_2db){var n=d.byId(node),s=gcs(n),mb=d._getMarginBox(n,s);var abs=d._abs(n,_2db);mb.x=abs.x;mb.y=abs.y;return mb;};var _2e0=d.isIE<8;var _2e1=function(name){switch(name.toLowerCase()){case "tabindex":return _2e0?"tabIndex":"tabindex";case "readonly":return "readOnly";case "class":return "className";case "for":case "htmlfor":return _2e0?"htmlFor":"for";default:return name;}};var _2e3={colspan:"colSpan",enctype:"enctype",frameborder:"frameborder",method:"method",rowspan:"rowSpan",scrolling:"scrolling",shape:"shape",span:"span",type:"type",valuetype:"valueType",classname:"className",innerhtml:"innerHTML"};dojo.hasAttr=function(node,name){node=d.byId(node);var _2e6=_2e1(name);_2e6=_2e6=="htmlFor"?"for":_2e6;var attr=node.getAttributeNode&&node.getAttributeNode(_2e6);return attr?attr.specified:false;};var _2e8={},_ctr=0,_2ea=dojo._scopeName+"attrid",_2eb={col:1,colgroup:1,table:1,tbody:1,tfoot:1,thead:1,tr:1,title:1};dojo.attr=function(node,name,_2ee){node=d.byId(node);var args=arguments.length;if(args==2&&!d.isString(name)){for(var x in name){d.attr(node,x,name[x]);}return;}name=_2e1(name);if(args==3){if(d.isFunction(_2ee)){var _2f1=d.attr(node,_2ea);if(!_2f1){_2f1=_ctr++;d.attr(node,_2ea,_2f1);}if(!_2e8[_2f1]){_2e8[_2f1]={};}var h=_2e8[_2f1][name];if(h){d.disconnect(h);}else{try{delete node[name];}catch(e){}}_2e8[_2f1][name]=d.connect(node,name,_2ee);}else{if(typeof _2ee=="boolean"){node[name]=_2ee;}else{if(name==="style"&&!d.isString(_2ee)){d.style(node,_2ee);}else{if(name=="className"){node.className=_2ee;}else{if(name==="innerHTML"){if(d.isIE&&node.tagName.toLowerCase() in _2eb){d.empty(node);node.appendChild(d._toDom(_2ee,node.ownerDocument));}else{node[name]=_2ee;}}else{node.setAttribute(name,_2ee);}}}}}}else{var prop=_2e3[name.toLowerCase()];if(prop){return node[prop];}var _2f4=node[name];return (typeof _2f4=="boolean"||typeof _2f4=="function")?_2f4:(d.hasAttr(node,name)?node.getAttribute(name):null);}};dojo.removeAttr=function(node,name){d.byId(node).removeAttribute(_2e1(name));};dojo.create=function(tag,_2f8,_2f9,pos){var doc=d.doc;if(_2f9){_2f9=d.byId(_2f9);doc=_2f9.ownerDocument;}if(d.isString(tag)){tag=doc.createElement(tag);}if(_2f8){d.attr(tag,_2f8);}if(_2f9){d.place(tag,_2f9,pos);}return tag;};d.empty=d.isIE?function(node){node=d.byId(node);for(var c;c=node.lastChild;){d.destroy(c);}}:function(node){d.byId(node).innerHTML="";};var _2ff={option:["select"],tbody:["table"],thead:["table"],tfoot:["table"],tr:["table","tbody"],td:["table","tbody","tr"],th:["table","thead","tr"],legend:["fieldset"],caption:["table"],colgroup:["table"],col:["table","colgroup"],li:["ul"]},_300=/<\s*([\w\:]+)/,_301={},_302=0,_303="__"+d._scopeName+"ToDomId";for(var _304 in _2ff){var tw=_2ff[_304];tw.pre=_304=="option"?"<select multiple=\"multiple\">":"<"+tw.join("><")+">";tw.post="</"+tw.reverse().join("></")+">";}d._toDom=function(frag,doc){doc=doc||d.doc;var _308=doc[_303];if(!_308){doc[_303]=_308=++_302+"";_301[_308]=doc.createElement("div");}frag+="";var _309=frag.match(_300),tag=_309?_309[1].toLowerCase():"",_30b=_301[_308],wrap,i,fc,df;if(_309&&_2ff[tag]){wrap=_2ff[tag];_30b.innerHTML=wrap.pre+frag+wrap.post;for(i=wrap.length;i;--i){_30b=_30b.firstChild;}}else{_30b.innerHTML=frag;}if(_30b.childNodes.length==1){return _30b.removeChild(_30b.firstChild);}df=doc.createDocumentFragment();while(fc=_30b.firstChild){df.appendChild(fc);}return df;};var _30f="className";dojo.hasClass=function(node,_311){return ((" "+d.byId(node)[_30f]+" ").indexOf(" "+_311+" ")>=0);};dojo.addClass=function(node,_313){node=d.byId(node);var cls=node[_30f];if((" "+cls+" ").indexOf(" "+_313+" ")<0){node[_30f]=cls+(cls?" ":"")+_313;}};dojo.removeClass=function(node,_316){node=d.byId(node);var t=d.trim((" "+node[_30f]+" ").replace(" "+_316+" "," "));if(node[_30f]!=t){node[_30f]=t;}};dojo.toggleClass=function(node,_319,_31a){if(_31a===undefined){_31a=!d.hasClass(node,_319);}d[_31a?"addClass":"removeClass"](node,_319);};})();}if(!dojo._hasResource["dojo._base.NodeList"]){dojo._hasResource["dojo._base.NodeList"]=true;dojo.provide("dojo._base.NodeList");(function(){var d=dojo;var ap=Array.prototype,aps=ap.slice,apc=ap.concat;var tnl=function(a){a.constructor=d.NodeList;dojo._mixin(a,d.NodeList.prototype);return a;};var _321=function(f,a,o){a=[0].concat(aps.call(a,0));o=o||d.global;return function(node){a[0]=node;return f.apply(o,a);};};var _326=function(f,o){return function(){this.forEach(_321(f,arguments,o));return this;};};var _329=function(f,o){return function(){return this.map(_321(f,arguments,o));};};var _32c=function(f,o){return function(){return this.filter(_321(f,arguments,o));};};var _32f=function(f,g,o){return function(){var a=arguments,body=_321(f,a,o);if(g.call(o||d.global,a)){return this.map(body);}this.forEach(body);return this;};};var _335=function(a){return a.length==1&&d.isString(a[0]);};var _337=function(node){var p=node.parentNode;if(p){p.removeChild(node);}};dojo.NodeList=function(){return tnl(Array.apply(null,arguments));};var nl=d.NodeList,nlp=nl.prototype;nl._wrap=tnl;nl._adaptAsMap=_329;nl._adaptAsForEach=_326;nl._adaptAsFilter=_32c;nl._adaptWithCondition=_32f;d.forEach(["slice","splice"],function(name){var f=ap[name];nlp[name]=function(){return tnl(f.apply(this,arguments));};});d.forEach(["indexOf","lastIndexOf","every","some"],function(name){var f=d[name];nlp[name]=function(){return f.apply(d,[this].concat(aps.call(arguments,0)));};});d.forEach(["attr","style"],function(name){nlp[name]=_32f(d[name],_335);});d.forEach(["connect","addClass","removeClass","toggleClass","empty"],function(name){nlp[name]=_326(d[name]);});dojo.extend(dojo.NodeList,{concat:function(item){var t=d.isArray(this)?this:aps.call(this,0),m=d.map(arguments,function(a){return a&&!d.isArray(a)&&(a.constructor===NodeList||a.constructor==nl)?aps.call(a,0):a;});return tnl(apc.apply(t,m));},map:function(func,obj){return tnl(d.map(this,func,obj));},forEach:function(_348,_349){d.forEach(this,_348,_349);return this;},coords:_329(d.coords),place:function(_34a,_34b){var item=d.query(_34a)[0];return this.forEach(function(node){d.place(node,item,_34b);});},orphan:function(_34e){return (_34e?d._filterQueryResult(this,_34e):this).forEach(_337);},adopt:function(_34f,_350){return d.query(_34f).place(item[0],_350);},query:function(_351){if(!_351){return this;}var ret=this.map(function(node){return d.query(_351,node).filter(function(_354){return _354!==undefined;});});return tnl(apc.apply([],ret));},filter:function(_355){var a=arguments,_357=this,_358=0;if(d.isString(_355)){_357=d._filterQueryResult(this,a[0]);if(a.length==1){return _357;}_358=1;}return tnl(d.filter(_357,a[_358],a[_358+1]));},addContent:function(_359,_35a){var c=d.isString(_359)?d._toDom(_359,this[0]&&this[0].ownerDocument):_359,i,l=this.length-1;for(i=0;i<l;++i){d.place(c.cloneNode(true),this[i],_35a);}if(l>=0){d.place(c,this[l],_35a);}return this;},instantiate:function(_35d,_35e){var c=d.isFunction(_35d)?_35d:d.getObject(_35d);_35e=_35e||{};return this.forEach(function(node){new c(_35e,node);});},at:function(){var t=new dojo.NodeList();d.forEach(arguments,function(i){if(this[i]){t.push(this[i]);}},this);return t;}});d.forEach(["blur","focus","change","click","error","keydown","keypress","keyup","load","mousedown","mouseenter","mouseleave","mousemove","mouseout","mouseover","mouseup","submit"],function(evt){var _oe="on"+evt;nlp[_oe]=function(a,b){return this.connect(_oe,a,b);};});})();}if(!dojo._hasResource["dojo._base.query"]){dojo._hasResource["dojo._base.query"]=true;if(typeof dojo!="undefined"){dojo.provide("dojo._base.query");}(function(d){var trim=d.trim;var each=d.forEach;var qlc=d._queryListCtor=d.NodeList;var _36b=d.isString;var _36c=function(){return d.doc;};var _36d=(d.isWebKit&&((_36c().compatMode)=="BackCompat"));var _36e=!!_36c().firstChild["children"]?"children":"childNodes";var _36f=">~+";var _370=false;var _371=function(){return true;};var _372=function(_373){if(_36f.indexOf(_373.slice(-1))>=0){_373+=" * ";}else{_373+=" ";}var ts=function(s,e){return trim(_373.slice(s,e));};var _377=[];var _378=-1,_379=-1,_37a=-1,_37b=-1,_37c=-1,inId=-1,_37e=-1,lc="",cc="",_381;var x=0,ql=_373.length,_384=null,_cp=null;var _386=function(){if(_37e>=0){var tv=(_37e==x)?null:ts(_37e,x);_384[(_36f.indexOf(tv)<0)?"tag":"oper"]=tv;_37e=-1;}};var _388=function(){if(inId>=0){_384.id=ts(inId,x).replace(/\\/g,"");inId=-1;}};var _389=function(){if(_37c>=0){_384.classes.push(ts(_37c+1,x).replace(/\\/g,""));_37c=-1;}};var _38a=function(){_388();_386();_389();};var _38b=function(){_38a();if(_37b>=0){_384.pseudos.push({name:ts(_37b+1,x)});}_384.loops=(_384.pseudos.length||_384.attrs.length||_384.classes.length);_384.oquery=_384.query=ts(_381,x);_384.otag=_384.tag=(_384["oper"])?null:(_384.tag||"*");if(_384.tag){_384.tag=_384.tag.toUpperCase();}if(_377.length&&(_377[_377.length-1].oper)){_384.infixOper=_377.pop();_384.query=_384.infixOper.query+" "+_384.query;}_377.push(_384);_384=null;};for(;lc=cc,cc=_373.charAt(x),x<ql;x++){if(lc=="\\"){continue;}if(!_384){_381=x;_384={query:null,pseudos:[],attrs:[],classes:[],tag:null,oper:null,id:null,getTag:function(){return (_370)?this.otag:this.tag;}};_37e=x;}if(_378>=0){if(cc=="]"){if(!_cp.attr){_cp.attr=ts(_378+1,x);}else{_cp.matchFor=ts((_37a||_378+1),x);}var cmf=_cp.matchFor;if(cmf){if((cmf.charAt(0)=="\"")||(cmf.charAt(0)=="'")){_cp.matchFor=cmf.slice(1,-1);}}_384.attrs.push(_cp);_cp=null;_378=_37a=-1;}else{if(cc=="="){var _38d=("|~^$*".indexOf(lc)>=0)?lc:"";_cp.type=_38d+cc;_cp.attr=ts(_378+1,x-_38d.length);_37a=x+1;}}}else{if(_379>=0){if(cc==")"){if(_37b>=0){_cp.value=ts(_379+1,x);}_37b=_379=-1;}}else{if(cc=="#"){_38a();inId=x+1;}else{if(cc=="."){_38a();_37c=x;}else{if(cc==":"){_38a();_37b=x;}else{if(cc=="["){_38a();_378=x;_cp={};}else{if(cc=="("){if(_37b>=0){_cp={name:ts(_37b+1,x),value:null};_384.pseudos.push(_cp);}_379=x;}else{if((cc==" ")&&(lc!=cc)){_38b();}}}}}}}}}return _377;};var _38e=function(_38f,_390){if(!_38f){return _390;}if(!_390){return _38f;}return function(){return _38f.apply(window,arguments)&&_390.apply(window,arguments);};};var _391=function(i,arr){var r=arr||[];if(i){r.push(i);}return r;};var _395=function(n){return (1==n.nodeType);};var _397="";var _398=function(elem,attr){if(!elem){return _397;}if(attr=="class"){return elem.className||_397;}if(attr=="for"){return elem.htmlFor||_397;}if(attr=="style"){return elem.style.cssText||_397;}return (_370?elem.getAttribute(attr):elem.getAttribute(attr,2))||_397;};var _39b={"*=":function(attr,_39d){return function(elem){return (_398(elem,attr).indexOf(_39d)>=0);};},"^=":function(attr,_3a0){return function(elem){return (_398(elem,attr).indexOf(_3a0)==0);};},"$=":function(attr,_3a3){var tval=" "+_3a3;return function(elem){var ea=" "+_398(elem,attr);return (ea.lastIndexOf(_3a3)==(ea.length-_3a3.length));};},"~=":function(attr,_3a8){var tval=" "+_3a8+" ";return function(elem){var ea=" "+_398(elem,attr)+" ";return (ea.indexOf(tval)>=0);};},"|=":function(attr,_3ad){var _3ae=" "+_3ad+"-";return function(elem){var ea=" "+_398(elem,attr);return ((ea==_3ad)||(ea.indexOf(_3ae)==0));};},"=":function(attr,_3b2){return function(elem){return (_398(elem,attr)==_3b2);};}};var _3b4=(typeof _36c().firstChild.nextElementSibling=="undefined");var _ns=!_3b4?"nextElementSibling":"nextSibling";var _ps=!_3b4?"previousElementSibling":"previousSibling";var _3b7=(_3b4?_395:_371);var _3b8=function(node){while(node=node[_ps]){if(_3b7(node)){return false;}}return true;};var _3ba=function(node){while(node=node[_ns]){if(_3b7(node)){return false;}}return true;};var _3bc=function(node){var root=node.parentNode;var i=0,tret=root[_36e],ci=(node["_i"]||-1),cl=(root["_l"]||-1);if(!tret){return -1;}var l=tret.length;if(cl==l&&ci>=0&&cl>=0){return ci;}root["_l"]=l;ci=-1;for(var te=root["firstElementChild"]||root["firstChild"];te;te=te[_ns]){if(_3b7(te)){te["_i"]=++i;if(node===te){ci=i;}}}return ci;};var _3c5=function(elem){return !((_3bc(elem))%2);};var _3c7=function(elem){return ((_3bc(elem))%2);};var _3c9={"checked":function(name,_3cb){return function(elem){return !!d.attr(elem,"checked");};},"first-child":function(){return _3b8;},"last-child":function(){return _3ba;},"only-child":function(name,_3ce){return function(node){if(!_3b8(node)){return false;}if(!_3ba(node)){return false;}return true;};},"empty":function(name,_3d1){return function(elem){var cn=elem.childNodes;var cnl=elem.childNodes.length;for(var x=cnl-1;x>=0;x--){var nt=cn[x].nodeType;if((nt===1)||(nt==3)){return false;}}return true;};},"contains":function(name,_3d8){var cz=_3d8.charAt(0);if(cz=="\""||cz=="'"){_3d8=_3d8.slice(1,-1);}return function(elem){return (elem.innerHTML.indexOf(_3d8)>=0);};},"not":function(name,_3dc){var p=_372(_3dc)[0];var _3de={el:1};if(p.tag!="*"){_3de.tag=1;}if(!p.classes.length){_3de.classes=1;}var ntf=_3e0(p,_3de);return function(elem){return (!ntf(elem));};},"nth-child":function(name,_3e3){var pi=parseInt;if(_3e3=="odd"){return _3c7;}else{if(_3e3=="even"){return _3c5;}}if(_3e3.indexOf("n")!=-1){var _3e5=_3e3.split("n",2);var pred=_3e5[0]?((_3e5[0]=="-")?-1:pi(_3e5[0])):1;var idx=_3e5[1]?pi(_3e5[1]):0;var lb=0,ub=-1;if(pred>0){if(idx<0){idx=(idx%pred)&&(pred+(idx%pred));}else{if(idx>0){if(idx>=pred){lb=idx-idx%pred;}idx=idx%pred;}}}else{if(pred<0){pred*=-1;if(idx>0){ub=idx;idx=idx%pred;}}}if(pred>0){return function(elem){var i=_3bc(elem);return (i>=lb)&&(ub<0||i<=ub)&&((i%pred)==idx);};}else{_3e3=idx;}}var _3ec=pi(_3e3);return function(elem){return (_3bc(elem)==_3ec);};}};var _3ee=(d.isIE)?function(cond){var clc=cond.toLowerCase();if(clc=="class"){cond="className";}return function(elem){return (_370?elem.getAttribute(cond):elem[cond]||elem[clc]);};}:function(cond){return function(elem){return (elem&&elem.getAttribute&&elem.hasAttribute(cond));};};var _3e0=function(_3f4,_3f5){if(!_3f4){return _371;}_3f5=_3f5||{};var ff=null;if(!("el" in _3f5)){ff=_38e(ff,_395);}if(!("tag" in _3f5)){if(_3f4.tag!="*"){ff=_38e(ff,function(elem){return (elem&&(elem.tagName==_3f4.getTag()));});}}if(!("classes" in _3f5)){each(_3f4.classes,function(_3f8,idx,arr){var re=new RegExp("(?:^|\\s)"+_3f8+"(?:\\s|$)");ff=_38e(ff,function(elem){return re.test(elem.className);});ff.count=idx;});}if(!("pseudos" in _3f5)){each(_3f4.pseudos,function(_3fd){var pn=_3fd.name;if(_3c9[pn]){ff=_38e(ff,_3c9[pn](pn,_3fd.value));}});}if(!("attrs" in _3f5)){each(_3f4.attrs,function(attr){var _400;var a=attr.attr;if(attr.type&&_39b[attr.type]){_400=_39b[attr.type](a,attr.matchFor);}else{if(a.length){_400=_3ee(a);}}if(_400){ff=_38e(ff,_400);}});}if(!("id" in _3f5)){if(_3f4.id){ff=_38e(ff,function(elem){return (!!elem&&(elem.id==_3f4.id));});}}if(!ff){if(!("default" in _3f5)){ff=_371;}}return ff;};var _403=function(_404){return function(node,ret,bag){while(node=node[_ns]){if(_3b4&&(!_395(node))){continue;}if((!bag||_408(node,bag))&&_404(node)){ret.push(node);}break;}return ret;};};var _409=function(_40a){return function(root,ret,bag){var te=root[_ns];while(te){if(_3b7(te)){if(bag&&!_408(te,bag)){break;}if(_40a(te)){ret.push(te);}}te=te[_ns];}return ret;};};var _40f=function(_410){_410=_410||_371;return function(root,ret,bag){var te,x=0,tret=root[_36e];while(te=tret[x++]){if(_3b7(te)&&(!bag||_408(te,bag))&&(_410(te,x))){ret.push(te);}}return ret;};};var _417=function(node,root){var pn=node.parentNode;while(pn){if(pn==root){break;}pn=pn.parentNode;}return !!pn;};var _41b={};var _41c=function(_41d){var _41e=_41b[_41d.query];if(_41e){return _41e;}var io=_41d.infixOper;var oper=(io?io.oper:"");var _421=_3e0(_41d,{el:1});var qt=_41d.tag;var _423=("*"==qt);var ecs=_36c()["getElementsByClassName"];if(!oper){if(_41d.id){_421=(!_41d.loops&&_423)?_371:_3e0(_41d,{el:1,id:1});_41e=function(root,arr){var te=d.byId(_41d.id,(root.ownerDocument||root));if(!te||!_421(te)){return;}if(9==root.nodeType){return _391(te,arr);}else{if(_417(te,root)){return _391(te,arr);}}};}else{if(ecs&&/\{\s*\[native code\]\s*\}/.test(String(ecs))&&_41d.classes.length&&!_36d){_421=_3e0(_41d,{el:1,classes:1,id:1});var _428=_41d.classes.join(" ");_41e=function(root,arr,bag){var ret=_391(0,arr),te,x=0;var tret=root.getElementsByClassName(_428);while((te=tret[x++])){if(_421(te,root)&&_408(te,bag)){ret.push(te);}}return ret;};}else{if(!_423&&!_41d.loops){_41e=function(root,arr,bag){var ret=_391(0,arr),te,x=0;var tret=root.getElementsByTagName(_41d.getTag());while((te=tret[x++])){if(_408(te,bag)){ret.push(te);}}return ret;};}else{_421=_3e0(_41d,{el:1,tag:1,id:1});_41e=function(root,arr,bag){var ret=_391(0,arr),te,x=0;var tret=root.getElementsByTagName(_41d.getTag());while((te=tret[x++])){if(_421(te,root)&&_408(te,bag)){ret.push(te);}}return ret;};}}}}else{var _43e={el:1};if(_423){_43e.tag=1;}_421=_3e0(_41d,_43e);if("+"==oper){_41e=_403(_421);}else{if("~"==oper){_41e=_409(_421);}else{if(">"==oper){_41e=_40f(_421);}}}}return _41b[_41d.query]=_41e;};var _43f=function(root,_441){var _442=_391(root),qp,x,te,qpl=_441.length,bag,ret;for(var i=0;i<qpl;i++){ret=[];qp=_441[i];x=_442.length-1;if(x>0){bag={};ret.nozip=true;}var gef=_41c(qp);while(te=_442[x--]){gef(te,ret,bag);}if(!ret.length){break;}_442=ret;}return ret;};var _44b={},_44c={};var _44d=function(_44e){var _44f=_372(trim(_44e));if(_44f.length==1){var tef=_41c(_44f[0]);return function(root){var r=tef(root,new qlc());if(r){r.nozip=true;}return r;};}return function(root){return _43f(root,_44f);};};var nua=navigator.userAgent;var wk="WebKit/";var _456=(d.isWebKit&&(nua.indexOf(wk)>0)&&(parseFloat(nua.split(wk)[1])>528));var _457=d.isIE?"commentStrip":"nozip";var qsa="querySelectorAll";var _459=(!!_36c()[qsa]&&(!d.isSafari||(d.isSafari>3.1)||_456));var _45a=function(_45b,_45c){if(_459){var _45d=_44c[_45b];if(_45d&&!_45c){return _45d;}}var _45e=_44b[_45b];if(_45e){return _45e;}var qcz=_45b.charAt(0);var _460=(-1==_45b.indexOf(" "));if((_45b.indexOf("#")>=0)&&(_460)){_45c=true;}var _461=(_459&&(!_45c)&&(_36f.indexOf(qcz)==-1)&&(!d.isIE||(_45b.indexOf(":")==-1))&&(!(_36d&&(_45b.indexOf(".")>=0)))&&(_45b.indexOf(":contains")==-1)&&(_45b.indexOf("|=")==-1));if(_461){var tq=(_36f.indexOf(_45b.charAt(_45b.length-1))>=0)?(_45b+" *"):_45b;return _44c[_45b]=function(root){try{if(!((9==root.nodeType)||_460)){throw "";}var r=root[qsa](tq);r[_457]=true;return r;}catch(e){return _45a(_45b,true)(root);}};}else{var _465=_45b.split(/\s*,\s*/);return _44b[_45b]=((_465.length<2)?_44d(_45b):function(root){var _467=0,ret=[],tp;while((tp=_465[_467++])){ret=ret.concat(_44d(tp)(root));}return ret;});}};var _46a=0;var _46b=d.isIE?function(node){if(_370){return (node.getAttribute("_uid")||node.setAttribute("_uid",++_46a)||_46a);}else{return node.uniqueID;}}:function(node){return (node._uid||(node._uid=++_46a));};var _408=function(node,bag){if(!bag){return 1;}var id=_46b(node);if(!bag[id]){return bag[id]=1;}return 0;};var _471="_zipIdx";var _zip=function(arr){if(arr&&arr.nozip){return (qlc._wrap)?qlc._wrap(arr):arr;}var ret=new qlc();if(!arr||!arr.length){return ret;}if(arr[0]){ret.push(arr[0]);}if(arr.length<2){return ret;}_46a++;if(d.isIE&&_370){var _475=_46a+"";arr[0].setAttribute(_471,_475);for(var x=1,te;te=arr[x];x++){if(arr[x].getAttribute(_471)!=_475){ret.push(te);}te.setAttribute(_471,_475);}}else{if(d.isIE&&arr.commentStrip){try{for(var x=1,te;te=arr[x];x++){if(_395(te)){ret.push(te);}}}catch(e){}}else{if(arr[0]){arr[0][_471]=_46a;}for(var x=1,te;te=arr[x];x++){if(arr[x][_471]!=_46a){ret.push(te);}te[_471]=_46a;}}}return ret;};d.query=function(_478,root){qlc=d._queryListCtor;if(!_478){return new qlc();}if(_478.constructor==qlc){return _478;}if(!_36b(_478)){return new qlc(_478);}if(_36b(root)){root=d.byId(root);if(!root){return new qlc();}}root=root||_36c();var od=root.ownerDocument||root.documentElement;_370=(root.contentType&&root.contentType=="application/xml")||(d.isOpera&&(root.doctype||od.toString()=="[object XMLDocument]"))||(!!od)&&(d.isIE?od.xml:(root.xmlVersion||od.xmlVersion));var r=_45a(_478)(root);if(r&&r.nozip&&!qlc._wrap){return r;}return _zip(r);};d.query.pseudos=_3c9;d._filterQueryResult=function(_47c,_47d){var _47e=new d._queryListCtor();var _47f=_3e0(_372(_47d)[0]);for(var x=0,te;te=_47c[x];x++){if(_47f(te)){_47e.push(te);}}return _47e;};})(this["queryPortability"]||this["acme"]||dojo);}if(!dojo._hasResource["dojo._base.xhr"]){dojo._hasResource["dojo._base.xhr"]=true;dojo.provide("dojo._base.xhr");(function(){var _d=dojo;function _483(obj,name,_486){var val=obj[name];if(_d.isString(val)){obj[name]=[val,_486];}else{if(_d.isArray(val)){val.push(_486);}else{obj[name]=_486;}}};dojo.formToObject=function(_488){var ret={};var _48a="file|submit|image|reset|button|";_d.forEach(dojo.byId(_488).elements,function(item){var _in=item.name;var type=(item.type||"").toLowerCase();if(_in&&type&&_48a.indexOf(type)==-1&&!item.disabled){if(type=="radio"||type=="checkbox"){if(item.checked){_483(ret,_in,item.value);}}else{if(item.multiple){ret[_in]=[];_d.query("option",item).forEach(function(opt){if(opt.selected){_483(ret,_in,opt.value);}});}else{_483(ret,_in,item.value);if(type=="image"){ret[_in+".x"]=ret[_in+".y"]=ret[_in].x=ret[_in].y=0;}}}}});return ret;};dojo.objectToQuery=function(map){var enc=encodeURIComponent;var _491=[];var _492={};for(var name in map){var _494=map[name];if(_494!=_492[name]){var _495=enc(name)+"=";if(_d.isArray(_494)){for(var i=0;i<_494.length;i++){_491.push(_495+enc(_494[i]));}}else{_491.push(_495+enc(_494));}}}return _491.join("&");};dojo.formToQuery=function(_497){return _d.objectToQuery(_d.formToObject(_497));};dojo.formToJson=function(_498,_499){return _d.toJson(_d.formToObject(_498),_499);};dojo.queryToObject=function(str){var ret={};var qp=str.split("&");var dec=decodeURIComponent;_d.forEach(qp,function(item){if(item.length){var _49f=item.split("=");var name=dec(_49f.shift());var val=dec(_49f.join("="));if(_d.isString(ret[name])){ret[name]=[ret[name]];}if(_d.isArray(ret[name])){ret[name].push(val);}else{ret[name]=val;}}});return ret;};dojo._blockAsync=false;dojo._contentHandlers={text:function(xhr){return xhr.responseText;},json:function(xhr){return _d.fromJson(xhr.responseText||null);},"json-comment-filtered":function(xhr){if(!dojo.config.useCommentedJson){console.warn("Consider using the standard mimetype:application/json."+" json-commenting can introduce security issues. To"+" decrease the chances of hijacking, use the standard the 'json' handler and"+" prefix your json with: {}&&\n"+"Use djConfig.useCommentedJson=true to turn off this message.");}var _4a5=xhr.responseText;var _4a6=_4a5.indexOf("/*");var _4a7=_4a5.lastIndexOf("*/");if(_4a6==-1||_4a7==-1){throw new Error("JSON was not comment filtered");}return _d.fromJson(_4a5.substring(_4a6+2,_4a7));},javascript:function(xhr){return _d.eval(xhr.responseText);},xml:function(xhr){var _4aa=xhr.responseXML;if(_d.isIE&&(!_4aa||!_4aa.documentElement)){var ms=function(n){return "MSXML"+n+".DOMDocument";};var dp=["Microsoft.XMLDOM",ms(6),ms(4),ms(3),ms(2)];_d.some(dp,function(p){try{var dom=new ActiveXObject(p);dom.async=false;dom.loadXML(xhr.responseText);_4aa=dom;}catch(e){return false;}return true;});}return _4aa;}};dojo._contentHandlers["json-comment-optional"]=function(xhr){var _4b1=_d._contentHandlers;if(xhr.responseText&&xhr.responseText.indexOf("/*")!=-1){return _4b1["json-comment-filtered"](xhr);}else{return _4b1["json"](xhr);}};dojo._ioSetArgs=function(args,_4b3,_4b4,_4b5){var _4b6={args:args,url:args.url};var _4b7=null;if(args.form){var form=_d.byId(args.form);var _4b9=form.getAttributeNode("action");_4b6.url=_4b6.url||(_4b9?_4b9.value:null);_4b7=_d.formToObject(form);}var _4ba=[{}];if(_4b7){_4ba.push(_4b7);}if(args.content){_4ba.push(args.content);}if(args.preventCache){_4ba.push({"dojo.preventCache":new Date().valueOf()});}_4b6.query=_d.objectToQuery(_d.mixin.apply(null,_4ba));_4b6.handleAs=args.handleAs||"text";var d=new _d.Deferred(_4b3);d.addCallbacks(_4b4,function(_4bc){return _4b5(_4bc,d);});var ld=args.load;if(ld&&_d.isFunction(ld)){d.addCallback(function(_4be){return ld.call(args,_4be,_4b6);});}var err=args.error;if(err&&_d.isFunction(err)){d.addErrback(function(_4c0){return err.call(args,_4c0,_4b6);});}var _4c1=args.handle;if(_4c1&&_d.isFunction(_4c1)){d.addBoth(function(_4c2){return _4c1.call(args,_4c2,_4b6);});}d.ioArgs=_4b6;return d;};var _4c3=function(dfd){dfd.canceled=true;var xhr=dfd.ioArgs.xhr;var _at=typeof xhr.abort;if(_at=="function"||_at=="object"||_at=="unknown"){xhr.abort();}var err=dfd.ioArgs.error;if(!err){err=new Error("xhr cancelled");err.dojoType="cancel";}return err;};var _4c8=function(dfd){var ret=_d._contentHandlers[dfd.ioArgs.handleAs](dfd.ioArgs.xhr);return ret===undefined?null:ret;};var _4cb=function(_4cc,dfd){console.error(_4cc);return _4cc;};var _4ce=null;var _4cf=[];var _4d0=function(){var now=(new Date()).getTime();if(!_d._blockAsync){for(var i=0,tif;i<_4cf.length&&(tif=_4cf[i]);i++){var dfd=tif.dfd;var func=function(){if(!dfd||dfd.canceled||!tif.validCheck(dfd)){_4cf.splice(i--,1);}else{if(tif.ioCheck(dfd)){_4cf.splice(i--,1);tif.resHandle(dfd);}else{if(dfd.startTime){if(dfd.startTime+(dfd.ioArgs.args.timeout||0)<now){_4cf.splice(i--,1);var err=new Error("timeout exceeded");err.dojoType="timeout";dfd.errback(err);dfd.cancel();}}}}};if(dojo.config.debugAtAllCosts){func.call(this);}else{try{func.call(this);}catch(e){dfd.errback(e);}}}}if(!_4cf.length){clearInterval(_4ce);_4ce=null;return;}};dojo._ioCancelAll=function(){try{_d.forEach(_4cf,function(i){try{i.dfd.cancel();}catch(e){}});}catch(e){}};if(_d.isIE){_d.addOnWindowUnload(_d._ioCancelAll);}_d._ioWatch=function(dfd,_4d9,_4da,_4db){var args=dfd.ioArgs.args;if(args.timeout){dfd.startTime=(new Date()).getTime();}_4cf.push({dfd:dfd,validCheck:_4d9,ioCheck:_4da,resHandle:_4db});if(!_4ce){_4ce=setInterval(_4d0,50);}if(args.sync){_4d0();}};var _4dd="application/x-www-form-urlencoded";var _4de=function(dfd){return dfd.ioArgs.xhr.readyState;};var _4e0=function(dfd){return 4==dfd.ioArgs.xhr.readyState;};var _4e2=function(dfd){var xhr=dfd.ioArgs.xhr;if(_d._isDocumentOk(xhr)){dfd.callback(dfd);}else{var err=new Error("Unable to load "+dfd.ioArgs.url+" status:"+xhr.status);err.status=xhr.status;err.responseText=xhr.responseText;dfd.errback(err);}};dojo._ioAddQueryToUrl=function(_4e6){if(_4e6.query.length){_4e6.url+=(_4e6.url.indexOf("?")==-1?"?":"&")+_4e6.query;_4e6.query=null;}};dojo.xhr=function(_4e7,args,_4e9){var dfd=_d._ioSetArgs(args,_4c3,_4c8,_4cb);dfd.ioArgs.xhr=_d._xhrObj(dfd.ioArgs.args);if(_4e9){if("postData" in args){dfd.ioArgs.query=args.postData;}else{if("putData" in args){dfd.ioArgs.query=args.putData;}}}else{_d._ioAddQueryToUrl(dfd.ioArgs);}var _4eb=dfd.ioArgs;var xhr=_4eb.xhr;xhr.open(_4e7,_4eb.url,args.sync!==true,args.user||undefined,args.password||undefined);if(args.headers){for(var hdr in args.headers){if(hdr.toLowerCase()==="content-type"&&!args.contentType){args.contentType=args.headers[hdr];}else{xhr.setRequestHeader(hdr,args.headers[hdr]);}}}xhr.setRequestHeader("Content-Type",args.contentType||_4dd);if(!args.headers||!args.headers["X-Requested-With"]){xhr.setRequestHeader("X-Requested-With","XMLHttpRequest");}if(dojo.config.debugAtAllCosts){xhr.send(_4eb.query);}else{try{xhr.send(_4eb.query);}catch(e){dfd.ioArgs.error=e;dfd.cancel();}}_d._ioWatch(dfd,_4de,_4e0,_4e2);xhr=null;return dfd;};dojo.xhrGet=function(args){return _d.xhr("GET",args);};dojo.rawXhrPost=dojo.xhrPost=function(args){return _d.xhr("POST",args,true);};dojo.rawXhrPut=dojo.xhrPut=function(args){return _d.xhr("PUT",args,true);};dojo.xhrDelete=function(args){return _d.xhr("DELETE",args);};})();}if(!dojo._hasResource["dojo._base.fx"]){dojo._hasResource["dojo._base.fx"]=true;dojo.provide("dojo._base.fx");(function(){var d=dojo;var _4f3=d.mixin;dojo._Line=function(_4f4,end){this.start=_4f4;this.end=end;};dojo._Line.prototype.getValue=function(n){return ((this.end-this.start)*n)+this.start;};d.declare("dojo._Animation",null,{constructor:function(args){_4f3(this,args);if(d.isArray(this.curve)){this.curve=new d._Line(this.curve[0],this.curve[1]);}},duration:350,repeat:0,rate:10,_percent:0,_startRepeatCount:0,_fire:function(evt,args){if(this[evt]){if(dojo.config.debugAtAllCosts){this[evt].apply(this,args||[]);}else{try{this[evt].apply(this,args||[]);}catch(e){console.error("exception in animation handler for:",evt);console.error(e);}}}return this;},play:function(_4fa,_4fb){var _t=this;if(_t._delayTimer){_t._clearTimer();}if(_4fb){_t._stopTimer();_t._active=_t._paused=false;_t._percent=0;}else{if(_t._active&&!_t._paused){return _t;}}_t._fire("beforeBegin");var de=_4fa||_t.delay,_p=dojo.hitch(_t,"_play",_4fb);if(de>0){_t._delayTimer=setTimeout(_p,de);return _t;}_p();return _t;},_play:function(_4ff){var _t=this;if(_t._delayTimer){_t._clearTimer();}_t._startTime=new Date().valueOf();if(_t._paused){_t._startTime-=_t.duration*_t._percent;}_t._endTime=_t._startTime+_t.duration;_t._active=true;_t._paused=false;var _501=_t.curve.getValue(_t._percent);if(!_t._percent){if(!_t._startRepeatCount){_t._startRepeatCount=_t.repeat;}_t._fire("onBegin",[_501]);}_t._fire("onPlay",[_501]);_t._cycle();return _t;},pause:function(){var _t=this;if(_t._delayTimer){_t._clearTimer();}_t._stopTimer();if(!_t._active){return _t;}_t._paused=true;_t._fire("onPause",[_t.curve.getValue(_t._percent)]);return _t;},gotoPercent:function(_503,_504){var _t=this;_t._stopTimer();_t._active=_t._paused=true;_t._percent=_503;if(_504){_t.play();}return _t;},stop:function(_506){var _t=this;if(_t._delayTimer){_t._clearTimer();}if(!_t._timer){return _t;}_t._stopTimer();if(_506){_t._percent=1;}_t._fire("onStop",[_t.curve.getValue(_t._percent)]);_t._active=_t._paused=false;return _t;},status:function(){if(this._active){return this._paused?"paused":"playing";}return "stopped";},_cycle:function(){var _t=this;if(_t._active){var curr=new Date().valueOf();var step=(curr-_t._startTime)/(_t._endTime-_t._startTime);if(step>=1){step=1;}_t._percent=step;if(_t.easing){step=_t.easing(step);}_t._fire("onAnimate",[_t.curve.getValue(step)]);if(_t._percent<1){_t._startTimer();}else{_t._active=false;if(_t.repeat>0){_t.repeat--;_t.play(null,true);}else{if(_t.repeat==-1){_t.play(null,true);}else{if(_t._startRepeatCount){_t.repeat=_t._startRepeatCount;_t._startRepeatCount=0;}}}_t._percent=0;_t._fire("onEnd");_t._stopTimer();}}return _t;},_clearTimer:function(){clearTimeout(this._delayTimer);delete this._delayTimer;}});var ctr=0,_50c=[],_50d=null,_50e={run:function(){}};dojo._Animation.prototype._startTimer=function(){if(!this._timer){this._timer=d.connect(_50e,"run",this,"_cycle");ctr++;}if(!_50d){_50d=setInterval(d.hitch(_50e,"run"),this.rate);}};dojo._Animation.prototype._stopTimer=function(){if(this._timer){d.disconnect(this._timer);this._timer=null;ctr--;}if(ctr<=0){clearInterval(_50d);_50d=null;ctr=0;}};var _50f=d.isIE?function(node){var ns=node.style;if(!ns.width.length&&d.style(node,"width")=="auto"){ns.width="auto";}}:function(){};dojo._fade=function(args){args.node=d.byId(args.node);var _513=_4f3({properties:{}},args),_514=(_513.properties.opacity={});_514.start=!("start" in _513)?function(){return +d.style(_513.node,"opacity")||0;}:_513.start;_514.end=_513.end;var anim=d.animateProperty(_513);d.connect(anim,"beforeBegin",d.partial(_50f,_513.node));return anim;};dojo.fadeIn=function(args){return d._fade(_4f3({end:1},args));};dojo.fadeOut=function(args){return d._fade(_4f3({end:0},args));};dojo._defaultEasing=function(n){return 0.5+((Math.sin((n+1.5)*Math.PI))/2);};var _519=function(_51a){this._properties=_51a;for(var p in _51a){var prop=_51a[p];if(prop.start instanceof d.Color){prop.tempColor=new d.Color();}}};_519.prototype.getValue=function(r){var ret={};for(var p in this._properties){var prop=this._properties[p],_521=prop.start;if(_521 instanceof d.Color){ret[p]=d.blendColors(_521,prop.end,r,prop.tempColor).toCss();}else{if(!d.isArray(_521)){ret[p]=((prop.end-_521)*r)+_521+(p!="opacity"?prop.units||"px":0);}}}return ret;};dojo.animateProperty=function(args){args.node=d.byId(args.node);if(!args.easing){args.easing=d._defaultEasing;}var anim=new d._Animation(args);d.connect(anim,"beforeBegin",anim,function(){var pm={};for(var p in this.properties){if(p=="width"||p=="height"){this.node.display="block";}var prop=this.properties[p];prop=pm[p]=_4f3({},(d.isObject(prop)?prop:{end:prop}));if(d.isFunction(prop.start)){prop.start=prop.start();}if(d.isFunction(prop.end)){prop.end=prop.end();}var _527=(p.toLowerCase().indexOf("color")>=0);function _528(node,p){var v={height:node.offsetHeight,width:node.offsetWidth}[p];if(v!==undefined){return v;}v=d.style(node,p);return (p=="opacity")?+v:(_527?v:parseFloat(v));};if(!("end" in prop)){prop.end=_528(this.node,p);}else{if(!("start" in prop)){prop.start=_528(this.node,p);}}if(_527){prop.start=new d.Color(prop.start);prop.end=new d.Color(prop.end);}else{prop.start=(p=="opacity")?+prop.start:parseFloat(prop.start);}}this.curve=new _519(pm);});d.connect(anim,"onAnimate",d.hitch(d,"style",anim.node));return anim;};dojo.anim=function(node,_52d,_52e,_52f,_530,_531){return d.animateProperty({node:node,duration:_52e||d._Animation.prototype.duration,properties:_52d,easing:_52f,onEnd:_530}).play(_531||0);};})();}if(!dojo._hasResource["dojo._base.browser"]){dojo._hasResource["dojo._base.browser"]=true;dojo.provide("dojo._base.browser");dojo.forEach(dojo.config.require,function(i){dojo["require"](i);});}if(dojo.config.afterOnLoad&&dojo.isBrowser){window.setTimeout(dojo._loadInit,1000);}})(); Property changes on: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js ___________________________________________________________________ Name: svn:mergeinfo + Deleted: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,8165 +0,0 @@ -/* - Copyright (c) 2004-2008, The Dojo Foundation - All Rights Reserved. - - Licensed under the Academic Free License version 2.1 or above OR the - modified BSD license. For more information on Dojo licensing, see: - - http://dojotoolkit.org/book/dojo-book-0-9/introduction/licensing -*/ - -/* - This is a compiled version of Dojo, built for deployment and not for - development. To get an editable version, please visit: - - http://dojotoolkit.org - - for documentation and information on getting the source. -*/ - -;(function(){ - - /* - dojo, dijit, and dojox must always be the first three, and in that order. - djConfig.scopeMap = [ - ["dojo", "fojo"], - ["dijit", "fijit"], - ["dojox", "fojox"] - - ] - */ - - /**Build will replace this comment with a scoped djConfig **/ - - //The null below can be relaced by a build-time value used instead of djConfig.scopeMap. - var sMap = null; - - //See if new scopes need to be defined. - if((sMap || (typeof djConfig != "undefined" && djConfig.scopeMap)) && (typeof window != "undefined")){ - var scopeDef = "", scopePrefix = "", scopeSuffix = "", scopeMap = {}, scopeMapRev = {}; - sMap = sMap || djConfig.scopeMap; - for(var i = 0; i < sMap.length; i++){ - //Make local variables, then global variables that use the locals. - var newScope = sMap[i]; - scopeDef += "var " + newScope[0] + " = {}; " + newScope[1] + " = " + newScope[0] + ";" + newScope[1] + "._scopeName = '" + newScope[1] + "';"; - scopePrefix += (i == 0 ? "" : ",") + newScope[0]; - scopeSuffix += (i == 0 ? "" : ",") + newScope[1]; - scopeMap[newScope[0]] = newScope[1]; - scopeMapRev[newScope[1]] = newScope[0]; - } - - eval(scopeDef + "dojo._scopeArgs = [" + scopeSuffix + "];"); - - dojo._scopePrefixArgs = scopePrefix; - dojo._scopePrefix = "(function(" + scopePrefix + "){"; - dojo._scopeSuffix = "})(" + scopeSuffix + ")"; - dojo._scopeMap = scopeMap; - dojo._scopeMapRev = scopeMapRev; - } - -/*===== -// note: -// 'djConfig' does not exist under 'dojo.*' so that it can be set before the -// 'dojo' variable exists. -// note: -// Setting any of these variables *after* the library has loaded does -// nothing at all. - -djConfig = { - // summary: - // Application code can set the global 'djConfig' prior to loading - // the library to override certain global settings for how dojo works. - // - // isDebug: Boolean - // Defaults to `false`. If set to `true`, ensures that Dojo provides - // extende debugging feedback via Firebug. If Firebug is not available - // on your platform, setting `isDebug` to `true` will force Dojo to - // pull in (and display) the version of Firebug Lite which is - // integrated into the Dojo distribution, thereby always providing a - // debugging/logging console when `isDebug` is enabled. Note that - // Firebug's `console.*` methods are ALWAYS defined by Dojo. If - // `isDebug` is false and you are on a platform without Firebug, these - // methods will be defined as no-ops. - isDebug: false, - // debugAtAllCosts: Boolean - // Defaults to `false`. If set to `true`, this triggers an alternate - // mode of the package system in which dependencies are detected and - // only then are resources evaluated in dependency order via - // `<script>` tag inclusion. This may double-request resources and - // cause problems with scripts which expect `dojo.require()` to - // preform synchronously. `debugAtAllCosts` can be an invaluable - // debugging aid, but when using it, ensure that all code which - // depends on Dojo modules is wrapped in `dojo.addOnLoad()` handlers. - // Due to the somewhat unpredictable side-effects of using - // `debugAtAllCosts`, it is strongly recommended that you enable this - // flag as a last resort. `debugAtAllCosts` has no effect when loading - // resources across domains. For usage information, see the - // [Dojo Book](http://dojotoolkit.org/book/book-dojo/part-4-meta-dojo-making-your-dojo-code-run-faster-and-better/debugging-facilities/deb) - debugAtAllCosts: false, - // locale: String - // The locale to assume for loading localized resources in this page, - // specified according to [RFC 3066](http://www.ietf.org/rfc/rfc3066.txt). - // Must be specified entirely in lowercase, e.g. `en-us` and `zh-cn`. - // See the documentation for `dojo.i18n` and `dojo.requireLocalization` - // for details on loading localized resources. If no locale is specified, - // Dojo assumes the locale of the user agent, according to `navigator.userLanguage` - // or `navigator.language` properties. - locale: undefined, - // extraLocale: Array - // No default value. Specifies additional locales whose - // resources should also be loaded alongside the default locale when - // calls to `dojo.requireLocalization()` are processed. - extraLocale: undefined, - // baseUrl: String - // The directory in which `dojo.js` is located. Under normal - // conditions, Dojo auto-detects the correct location from which it - // was loaded. You may need to manually configure `baseUrl` in cases - // where you have renamed `dojo.js` or in which `<base>` tags confuse - // some browsers (e.g., IE 6). The variable `dojo.baseUrl` is assigned - // either the value of `djConfig.baseUrl` if one is provided or the - // auto-detected root if not. Other modules are located relative to - // this path. - baseUrl: undefined, - // modulePaths: Object - // A map of module names to paths relative to `dojo.baseUrl`. The - // key/value pairs correspond directly to the arguments which - // `dojo.registerModulePath` accepts. Specifiying - // `djConfig.modulePaths = { "foo": "../../bar" }` is the equivalent - // of calling `dojo.registerModulePath("foo", "../../bar");`. Multiple - // modules may be configured via `djConfig.modulePaths`. - modulePaths: {}, -} -=====*/ - -(function(){ - // firebug stubs - - // if((!this["console"])||(!console["firebug"])){ - - if(!this["console"]){ - this.console = { - log: function(){} // no-op - }; - } - - var cn = [ - "assert", "count", "debug", "dir", "dirxml", "error", "group", - "groupEnd", "info", "profile", "profileEnd", "time", "timeEnd", - "trace", "warn", "log" - ]; - var i=0, tn; - while((tn=cn[i++])){ - if(!console[tn]){ - (function(){ - var tcn = tn+""; - console[tcn] = function(){ - var a = Array.apply({}, arguments); - a.unshift(tcn+":"); - console.log(a.join(" ")); - } - })(); - } - } - - //TODOC: HOW TO DOC THIS? - // dojo is the root variable of (almost all) our public symbols -- make sure it is defined. - if(typeof dojo == "undefined"){ - this.dojo = { - _scopeName: "dojo", - _scopePrefix: "", - _scopePrefixArgs: "", - _scopeSuffix: "", - _scopeMap: {}, - _scopeMapRev: {} - }; - } - - var d = dojo; - - //Need placeholders for dijit and dojox for scoping code. - if(typeof dijit == "undefined"){ - this.dijit = {_scopeName: "dijit"}; - } - if(typeof dojox == "undefined"){ - this.dojox = {_scopeName: "dojox"}; - } - - if(!d._scopeArgs){ - d._scopeArgs = [dojo, dijit, dojox]; - } - -/*===== -dojo.global = { - // summary: - // Alias for the global scope - // (e.g. the window object in a browser). - // description: - // Refer to 'dojo.global' rather than referring to window to ensure your - // code runs correctly in contexts other than web browsers (e.g. Rhino on a server). -} -=====*/ - d.global = this; - - d.config =/*===== djConfig = =====*/{ - isDebug: false, - debugAtAllCosts: false - }; - - if(typeof djConfig != "undefined"){ - for(var opt in djConfig){ - d.config[opt] = djConfig[opt]; - } - } - - var _platforms = ["Browser", "Rhino", "Spidermonkey", "Mobile"]; - var t; - while((t=_platforms.shift())){ - d["is"+t] = false; - } - -/*===== - // Override locale setting, if specified - dojo.locale = { - // summary: the locale as defined by Dojo (read-only) - }; -=====*/ - dojo.locale = d.config.locale; - - var rev = "$Rev: 13707 $".match(/\d+/); - - dojo.version = { - // summary: - // version number of dojo - // major: Integer - // Major version. If total version is "1.2.0beta1", will be 1 - // minor: Integer - // Minor version. If total version is "1.2.0beta1", will be 2 - // patch: Integer - // Patch version. If total version is "1.2.0beta1", will be 0 - // flag: String - // Descriptor flag. If total version is "1.2.0beta1", will be "beta1" - // revision: Number - // The SVN rev from which dojo was pulled - major: 1, minor: 1, patch: 1, flag: "", - revision: rev ? +rev[0] : 999999, //FIXME: use NaN? - toString: function(){ - with(d.version){ - return major + "." + minor + "." + patch + flag + " (" + revision + ")"; // String - } - } - } - - // Register with the OpenAjax hub - if(typeof OpenAjax != "undefined"){ - OpenAjax.hub.registerLibrary(dojo._scopeName, "http://dojotoolkit.org", d.version.toString()); - } - - dojo._mixin = function(/*Object*/ obj, /*Object*/ props){ - // summary: - // Adds all properties and methods of props to obj. This addition - // is "prototype extension safe", so that instances of objects - // will not pass along prototype defaults. - var tobj = {}; - for(var x in props){ - // the "tobj" condition avoid copying properties in "props" - // inherited from Object.prototype. For example, if obj has a custom - // toString() method, don't overwrite it with the toString() method - // that props inherited from Object.prototype - if(tobj[x] === undefined || tobj[x] != props[x]){ - obj[x] = props[x]; - } - } - // IE doesn't recognize custom toStrings in for..in - if(d["isIE"] && props){ - var p = props.toString; - if(typeof p == "function" && p != obj.toString && p != tobj.toString && - p != "\nfunction toString() {\n [native code]\n}\n"){ - obj.toString = props.toString; - } - } - return obj; // Object - } - - dojo.mixin = function(/*Object*/obj, /*Object...*/props){ - // summary: - // Adds all properties and methods of props to obj and returns the - // (now modified) obj. - // description: - // `dojo.mixin` can mix multiple source objects into a - // destionation object which is then returned. Unlike regular - // `for...in` iteration, `dojo.mixin` is also smart about avoiding - // extensions which other toolkits may unwisely add to the root - // object prototype - // obj: - // The object to mix properties into. Also the return value. - // props: - // One or more objects whose values are successively copied into - // obj. If more than one of these objects contain the same value, - // the one specified last in the function call will "win". - // example: - // make a shallow copy of an object - // | var copy = dojo.mixin({}, source); - // example: - // many class constructors often take an object which specifies - // values to be configured on the object. In this case, it is - // often simplest to call `dojo.mixin` on the `this` object: - // | dojo.declare("acme.Base", null, { - // | constructor: function(properties){ - // | // property configuration: - // | dojo.mixin(this, properties); - // | - // | console.debug(this.quip); - // | // ... - // | }, - // | quip: "I wasn't born yesterday, you know - I've seen movies.", - // | // ... - // | }); - // | - // | // create an instance of the class and configure it - // | var b = new acme.Base({quip: "That's what it does!" }); - // example: - // copy in properties from multiple objects - // | var flattened = dojo.mixin( - // | { - // | name: "Frylock", - // | braces: true, - // | } - // | { - // | name: "Carl Brutanananadilewski" - // | } - // | ); - // | - // | // will print "Carl Brutanananadilewski" - // | console.debug(flattened.name); - // | // will print "true" - // | console.debug(flattened.braces); - for(var i=1, l=arguments.length; i<l; i++){ - d._mixin(obj, arguments[i]); - } - return obj; // Object - } - - dojo._getProp = function(/*Array*/parts, /*Boolean*/create, /*Object*/context){ - var obj=context || d.global; - for(var i=0, p; obj && (p=parts[i]); i++){ - if(i == 0 && this._scopeMap[p]){ - p = this._scopeMap[p]; - } - obj = (p in obj ? obj[p] : (create ? obj[p]={} : undefined)); - } - return obj; // mixed - } - - dojo.setObject = function(/*String*/name, /*Object*/value, /*Object?*/context){ - // summary: - // Set a property from a dot-separated string, such as "A.B.C" - // description: - // Useful for longer api chains where you have to test each object in - // the chain, or when you have an object reference in string format. - // Objects are created as needed along `path`. Returns the passed - // value if setting is successful or `undefined` if not. - // name: - // Path to a property, in the form "A.B.C". - // context: - // Optional. Object to use as root of path. Defaults to - // `dojo.global`. - // example: - // set the value of `foo.bar.baz`, regardless of whether - // intermediate objects already exist: - // | dojo.setObject("foo.bar.baz", value); - // example: - // without `dojo.setObject`, we often see code like this: - // | // ensure that intermediate objects are available - // | if(!obj["parent"]){ obj.parent = {}; } - // | if(!obj.parent["child"]){ obj.parent.child= {}; } - // | // now we can safely set the property - // | obj.parent.child.prop = "some value"; - // wheras with `dojo.setObject`, we can shorten that to: - // | dojo.setObject("parent.child.prop", "some value", obj); - var parts=name.split("."), p=parts.pop(), obj=d._getProp(parts, true, context); - return obj && p ? (obj[p]=value) : undefined; // Object - } - - dojo.getObject = function(/*String*/name, /*Boolean*/create, /*Object*/context){ - // summary: - // Get a property from a dot-separated string, such as "A.B.C" - // description: - // Useful for longer api chains where you have to test each object in - // the chain, or when you have an object reference in string format. - // name: - // Path to an property, in the form "A.B.C". - // context: - // Optional. Object to use as root of path. Defaults to - // 'dojo.global'. Null may be passed. - // create: - // Optional. Defaults to `false`. If `true`, Objects will be - // created at any point along the 'path' that is undefined. - return d._getProp(name.split("."), create, context); // Object - } - - dojo.exists = function(/*String*/name, /*Object?*/obj){ - // summary: - // determine if an object supports a given method - // description: - // useful for longer api chains where you have to test each object in - // the chain - // name: - // Path to an object, in the form "A.B.C". - // obj: - // Object to use as root of path. Defaults to - // 'dojo.global'. Null may be passed. - // example: - // | // define an object - // | var foo = { - // | bar: { } - // | }; - // | - // | // search the global scope - // | dojo.exists("foo.bar"); // true - // | dojo.exists("foo.bar.baz"); // false - // | - // | // search from a particular scope - // | dojo.exists("bar", foo); // true - // | dojo.exists("bar.baz", foo); // false - return !!d.getObject(name, false, obj); // Boolean - } - - - dojo["eval"] = function(/*String*/ scriptFragment){ - // summary: - // Perform an evaluation in the global scope. Use this rather than - // calling 'eval()' directly. - // description: - // Placed in a separate function to minimize size of trapped - // exceptions. Calling eval() directly from some other scope may - // complicate tracebacks on some platforms. - // return: - // The result of the evaluation. Often `undefined` - - - // note: - // - JSC eval() takes an optional second argument which can be 'unsafe'. - // - Mozilla/SpiderMonkey eval() takes an optional second argument which is the - // scope object for new symbols. - - // FIXME: investigate Joseph Smarr's technique for IE: - // http://josephsmarr.com/2007/01/31/fixing-eval-to-use-global-scope-in-ie/ - // see also: - // http://trac.dojotoolkit.org/ticket/744 - return d.global.eval ? d.global.eval(scriptFragment) : eval(scriptFragment); // Object - } - - /*===== - dojo.deprecated = function(behaviour, extra, removal){ - // summary: - // Log a debug message to indicate that a behavior has been - // deprecated. - // behaviour: String - // The API or behavior being deprecated. Usually in the form - // of "myApp.someFunction()". - // extra: String? - // Text to append to the message. Often provides advice on a - // new function or facility to achieve the same goal during - // the deprecation period. - // removal: String? - // Text to indicate when in the future the behavior will be - // removed. Usually a version number. - // example: - // | dojo.deprecated("myApp.getTemp()", "use myApp.getLocaleTemp() instead", "1.0"); - } - - dojo.experimental = function(moduleName, extra){ - // summary: Marks code as experimental. - // description: - // This can be used to mark a function, file, or module as - // experimental. Experimental code is not ready to be used, and the - // APIs are subject to change without notice. Experimental code may be - // completed deleted without going through the normal deprecation - // process. - // moduleName: String - // The name of a module, or the name of a module file or a specific - // function - // extra: String? - // some additional message for the user - // example: - // | dojo.experimental("dojo.data.Result"); - // example: - // | dojo.experimental("dojo.weather.toKelvin()", "PENDING approval from NOAA"); - } - =====*/ - - //Real functions declared in dojo._firebug.firebug. - d.deprecated = d.experimental = function(){}; - -})(); -// vim:ai:ts=4:noet - -/* - * loader.js - A bootstrap module. Runs before the hostenv_*.js file. Contains - * all of the package loading methods. - */ - -(function(){ - var d = dojo; - - d.mixin(d, { - _loadedModules: {}, - _inFlightCount: 0, - _hasResource: {}, - - _modulePrefixes: { - dojo: { name: "dojo", value: "." }, - // dojox: { name: "dojox", value: "../dojox" }, - // dijit: { name: "dijit", value: "../dijit" }, - doh: { name: "doh", value: "../util/doh" }, - tests: { name: "tests", value: "tests" } - }, - - _moduleHasPrefix: function(/*String*/module){ - // summary: checks to see if module has been established - var mp = this._modulePrefixes; - return !!(mp[module] && mp[module].value); // Boolean - }, - - _getModulePrefix: function(/*String*/module){ - // summary: gets the prefix associated with module - var mp = this._modulePrefixes; - if(this._moduleHasPrefix(module)){ - return mp[module].value; // String - } - return module; // String - }, - - _loadedUrls: [], - - //WARNING: - // This variable is referenced by packages outside of bootstrap: - // FloatingPane.js and undo/browser.js - _postLoad: false, - - //Egad! Lots of test files push on this directly instead of using dojo.addOnLoad. - _loaders: [], - _unloaders: [], - _loadNotifying: false - }); - - - dojo._loadPath = function(/*String*/relpath, /*String?*/module, /*Function?*/cb){ - // summary: - // Load a Javascript module given a relative path - // - // description: - // Loads and interprets the script located at relpath, which is - // relative to the script root directory. If the script is found but - // its interpretation causes a runtime exception, that exception is - // not caught by us, so the caller will see it. We return a true - // value if and only if the script is found. - // - // relpath: - // A relative path to a script (no leading '/', and typically ending - // in '.js'). - // module: - // A module whose existance to check for after loading a path. Can be - // used to determine success or failure of the load. - // cb: - // a callback function to pass the result of evaluating the script - - var uri = ((relpath.charAt(0) == '/' || relpath.match(/^\w+:/)) ? "" : this.baseUrl) + relpath; - try{ - return !module ? this._loadUri(uri, cb) : this._loadUriAndCheck(uri, module, cb); // Boolean - }catch(e){ - console.error(e); - return false; // Boolean - } - } - - dojo._loadUri = function(/*String*/uri, /*Function?*/cb){ - // summary: - // Loads JavaScript from a URI - // description: - // Reads the contents of the URI, and evaluates the contents. This is - // used to load modules as well as resource bundles. Returns true if - // it succeeded. Returns false if the URI reading failed. Throws if - // the evaluation throws. - // uri: a uri which points at the script to be loaded - // cb: - // a callback function to process the result of evaluating the script - // as an expression, typically used by the resource bundle loader to - // load JSON-style resources - - if(this._loadedUrls[uri]){ - return true; // Boolean - } - var contents = this._getText(uri, true); - if(!contents){ return false; } // Boolean - this._loadedUrls[uri] = true; - this._loadedUrls.push(uri); - if(cb){ - contents = '('+contents+')'; - }else{ - //Only do the scoping if no callback. If a callback is specified, - //it is most likely the i18n bundle stuff. - contents = this._scopePrefix + contents + this._scopeSuffix; - } - if(d.isMoz){ contents += "\r\n//@ sourceURL=" + uri; } // debugging assist for Firebug - var value = d["eval"](contents); - if(cb){ cb(value); } - return true; // Boolean - } - - // FIXME: probably need to add logging to this method - dojo._loadUriAndCheck = function(/*String*/uri, /*String*/moduleName, /*Function?*/cb){ - // summary: calls loadUri then findModule and returns true if both succeed - var ok = false; - try{ - ok = this._loadUri(uri, cb); - }catch(e){ - console.error("failed loading " + uri + " with error: " + e); - } - return !!(ok && this._loadedModules[moduleName]); // Boolean - } - - dojo.loaded = function(){ - // summary: - // signal fired when initial environment and package loading is - // complete. You may use dojo.addOnLoad() or dojo.connect() to - // this method in order to handle initialization tasks that - // require the environment to be initialized. In a browser host, - // declarative widgets will be constructed when this function - // finishes runing. - this._loadNotifying = true; - this._postLoad = true; - var mll = d._loaders; - - //Clear listeners so new ones can be added - //For other xdomain package loads after the initial load. - this._loaders = []; - - for(var x = 0; x < mll.length; x++){ - try{ - mll[x](); - }catch(e){ - throw e; - console.error("dojo.addOnLoad callback failed: " + e, e); /* let other load events fire, like the parser, but report the error */ - } - } - - this._loadNotifying = false; - - //Make sure nothing else got added to the onload queue - //after this first run. If something did, and we are not waiting for any - //more inflight resources, run again. - if(d._postLoad && d._inFlightCount == 0 && mll.length){ - d._callLoaded(); - } - } - - dojo.unloaded = function(){ - // summary: - // signal fired by impending environment destruction. You may use - // dojo.addOnUnload() or dojo.connect() to this method to perform - // page/application cleanup methods. - var mll = this._unloaders; - while(mll.length){ - (mll.pop())(); - } - } - - var onto = function(arr, obj, fn){ - if(!fn){ - arr.push(obj); - }else if(fn){ - var func = (typeof fn == "string") ? obj[fn] : fn; - arr.push(function(){ func.call(obj); }); - } - } - - dojo.addOnLoad = function(/*Object?*/obj, /*String|Function*/functionName){ - // summary: - // Registers a function to be triggered after the DOM has finished - // loading and widgets declared in markup have been instantiated. - // Images and CSS files may or may not have finished downloading when - // the specified function is called. (Note that widgets' CSS and HTML - // code is guaranteed to be downloaded before said widgets are - // instantiated.) - // example: - // | dojo.addOnLoad(functionPointer); - // | dojo.addOnLoad(object, "functionName"); - // | dojo.addOnLoad(object, function(){ /* ... */}); - - onto(d._loaders, obj, functionName); - - //Added for xdomain loading. dojo.addOnLoad is used to - //indicate callbacks after doing some dojo.require() statements. - //In the xdomain case, if all the requires are loaded (after initial - //page load), then immediately call any listeners. - if(d._postLoad && d._inFlightCount == 0 && !d._loadNotifying){ - d._callLoaded(); - } - } - - dojo.addOnUnload = function(/*Object?*/obj, /*String|Function?*/functionName){ - // summary: - // registers a function to be triggered when the page unloads - // example: - // | dojo.addOnUnload(functionPointer) - // | dojo.addOnUnload(object, "functionName") - // | dojo.addOnUnload(object, function(){ /* ... */}); - - onto(d._unloaders, obj, functionName); - } - - dojo._modulesLoaded = function(){ - if(d._postLoad){ return; } - if(d._inFlightCount > 0){ - console.warn("files still in flight!"); - return; - } - d._callLoaded(); - } - - dojo._callLoaded = function(){ - - // The "object" check is for IE, and the other opera check fixes an - // issue in Opera where it could not find the body element in some - // widget test cases. For 0.9, maybe route all browsers through the - // setTimeout (need protection still for non-browser environments - // though). This might also help the issue with FF 2.0 and freezing - // issues where we try to do sync xhr while background css images are - // being loaded (trac #2572)? Consider for 0.9. - if(typeof setTimeout == "object" || (dojo.config.useXDomain && d.isOpera)){ - if(dojo.isAIR){ - setTimeout(function(){dojo.loaded();}, 0); - }else{ - setTimeout(dojo._scopeName + ".loaded();", 0); - } - }else{ - d.loaded(); - } - } - - dojo._getModuleSymbols = function(/*String*/modulename){ - // summary: - // Converts a module name in dotted JS notation to an array - // representing the path in the source tree - var syms = modulename.split("."); - for(var i = syms.length; i>0; i--){ - var parentModule = syms.slice(0, i).join("."); - if((i==1) && !this._moduleHasPrefix(parentModule)){ - // Support default module directory (sibling of dojo) for top-level modules - syms[0] = "../" + syms[0]; - }else{ - var parentModulePath = this._getModulePrefix(parentModule); - if(parentModulePath != parentModule){ - syms.splice(0, i, parentModulePath); - break; - } - } - } - // console.debug(syms); - return syms; // Array - } - - dojo._global_omit_module_check = false; - - dojo._loadModule = dojo.require = function(/*String*/moduleName, /*Boolean?*/omitModuleCheck){ - // summary: - // loads a Javascript module from the appropriate URI - // moduleName: - // module name to load. Module paths are de-referenced by dojo's - // internal mapping of locations to names and are disambiguated by - // longest prefix. See `dojo.registerModulePath()` for details on - // registering new modules. - // omitModuleCheck: - // if `true`, omitModuleCheck skips the step of ensuring that the - // loaded file actually defines the symbol it is referenced by. - // For example if it called as `dojo._loadModule("a.b.c")` and the - // file located at `a/b/c.js` does not define an object `a.b.c`, - // and exception will be throws whereas no exception is raised - // when called as `dojo._loadModule("a.b.c", true)` - // description: - // `dojo._loadModule("A.B")` first checks to see if symbol A.B is - // defined. If it is, it is simply returned (nothing to do). - // - // If it is not defined, it will look for `A/B.js` in the script root - // directory. - // - // `dojo._loadModule` throws an excpetion if it cannot find a file - // to load, or if the symbol `A.B` is not defined after loading. - // - // It returns the object `A.B`. - // - // `dojo._loadModule()` does nothing about importing symbols into - // the current namespace. It is presumed that the caller will - // take care of that. For example, to import all symbols into a - // local block, you might write: - // - // | with (dojo._loadModule("A.B")) { - // | ... - // | } - // - // And to import just the leaf symbol to a local variable: - // - // | var B = dojo._loadModule("A.B"); - // | ... - // returns: the required namespace object - omitModuleCheck = this._global_omit_module_check || omitModuleCheck; - - //Check if it is already loaded. - var module = this._loadedModules[moduleName]; - if(module){ - return module; - } - - // convert periods to slashes - var relpath = this._getModuleSymbols(moduleName).join("/") + '.js'; - - var modArg = (!omitModuleCheck) ? moduleName : null; - var ok = this._loadPath(relpath, modArg); - - if(!ok && !omitModuleCheck){ - throw new Error("Could not load '" + moduleName + "'; last tried '" + relpath + "'"); - } - - // check that the symbol was defined - // Don't bother if we're doing xdomain (asynchronous) loading. - if(!omitModuleCheck && !this._isXDomain){ - // pass in false so we can give better error - module = this._loadedModules[moduleName]; - if(!module){ - throw new Error("symbol '" + moduleName + "' is not defined after loading '" + relpath + "'"); - } - } - - return module; - } - - dojo.provide = function(/*String*/ resourceName){ - // summary: - // Each javascript source file must have at least one - // `dojo.provide()` call at the top of the file, corresponding to - // the file name. For example, `js/dojo/foo.js` must have - // `dojo.provide("dojo.foo");` before any calls to - // `dojo.require()` are made. - // description: - // Each javascript source file is called a resource. When a - // resource is loaded by the browser, `dojo.provide()` registers - // that it has been loaded. - // - // For backwards compatibility reasons, in addition to registering - // the resource, `dojo.provide()` also ensures that the javascript - // object for the module exists. For example, - // `dojo.provide("dojox.data.FlickrStore")`, in addition to - // registering that `FlickrStore.js` is a resource for the - // `dojox.data` module, will ensure that the `dojox.data` - // javascript object exists, so that calls like - // `dojo.data.foo = function(){ ... }` don't fail. - // - // In the case of a build where multiple javascript source files - // are combined into one bigger file (similar to a .lib or .jar - // file), that file may contain multiple dojo.provide() calls, to - // note that it includes multiple resources. - - //Make sure we have a string. - resourceName = resourceName + ""; - return (d._loadedModules[resourceName] = d.getObject(resourceName, true)); // Object - } - - //Start of old bootstrap2: - - dojo.platformRequire = function(/*Object*/modMap){ - // summary: - // require one or more modules based on which host environment - // Dojo is currently operating in - // description: - // This method takes a "map" of arrays which one can use to - // optionally load dojo modules. The map is indexed by the - // possible dojo.name_ values, with two additional values: - // "default" and "common". The items in the "default" array will - // be loaded if none of the other items have been choosen based on - // dojo.name_, set by your host environment. The items in the - // "common" array will *always* be loaded, regardless of which - // list is chosen. - // example: - // | dojo.platformRequire({ - // | browser: [ - // | "foo.sample", // simple module - // | "foo.test", - // | ["foo.bar.baz", true] // skip object check in _loadModule - // | ], - // | default: [ "foo.sample._base" ], - // | common: [ "important.module.common" ] - // | }); - - var common = modMap.common || []; - var result = common.concat(modMap[d._name] || modMap["default"] || []); - - for(var x=0; x<result.length; x++){ - var curr = result[x]; - if(curr.constructor == Array){ - d._loadModule.apply(d, curr); - }else{ - d._loadModule(curr); - } - } - } - - dojo.requireIf = function(/*Boolean*/ condition, /*String*/ resourceName){ - // summary: - // If the condition is true then call dojo.require() for the specified - // resource - if(condition === true){ - // FIXME: why do we support chained require()'s here? does the build system? - var args = []; - for(var i = 1; i < arguments.length; i++){ - args.push(arguments[i]); - } - d.require.apply(d, args); - } - } - - dojo.requireAfterIf = d.requireIf; - - dojo.registerModulePath = function(/*String*/module, /*String*/prefix){ - // summary: - // maps a module name to a path - // description: - // An unregistered module is given the default path of ../[module], - // relative to Dojo root. For example, module acme is mapped to - // ../acme. If you want to use a different module name, use - // dojo.registerModulePath. - // example: - // If your dojo.js is located at this location in the web root: - // | /myapp/js/dojo/dojo/dojo.js - // and your modules are located at: - // | /myapp/js/foo/bar.js - // | /myapp/js/foo/baz.js - // | /myapp/js/foo/thud/xyzzy.js - // Your application can tell Dojo to locate the "foo" namespace by calling: - // | dojo.registerModulePath("foo", "../../foo"); - // At which point you can then use dojo.require() to load the - // modules (assuming they provide() the same things which are - // required). The full code might be: - // | <script type="text/javascript" - // | src="/myapp/js/dojo/dojo/dojo.js"></script> - // | <script type="text/javascript"> - // | dojo.registerModulePath("foo", "../../foo"); - // | dojo.require("foo.bar"); - // | dojo.require("foo.baz"); - // | dojo.require("foo.thud.xyzzy"); - // | </script> - d._modulePrefixes[module] = { name: module, value: prefix }; - } - - dojo.requireLocalization = function(/*String*/moduleName, /*String*/bundleName, /*String?*/locale, /*String?*/availableFlatLocales){ - // summary: - // Declares translated resources and loads them if necessary, in the - // same style as dojo.require. Contents of the resource bundle are - // typically strings, but may be any name/value pair, represented in - // JSON format. See also dojo.i18n.getLocalization. - // moduleName: - // name of the package containing the "nls" directory in which the - // bundle is found - // bundleName: - // bundle name, i.e. the filename without the '.js' suffix - // locale: - // the locale to load (optional) By default, the browser's user - // locale as defined by dojo.locale - // availableFlatLocales: - // A comma-separated list of the available, flattened locales for this - // bundle. This argument should only be set by the build process. - // description: - // Load translated resource bundles provided underneath the "nls" - // directory within a package. Translated resources may be located in - // different packages throughout the source tree. For example, a - // particular widget may define one or more resource bundles, - // structured in a program as follows, where moduleName is - // mycode.mywidget and bundleNames available include bundleone and - // bundletwo: - // - // | ... - // | mycode/ - // | mywidget/ - // | nls/ - // | bundleone.js (the fallback translation, English in this example) - // | bundletwo.js (also a fallback translation) - // | de/ - // | bundleone.js - // | bundletwo.js - // | de-at/ - // | bundleone.js - // | en/ - // | (empty; use the fallback translation) - // | en-us/ - // | bundleone.js - // | en-gb/ - // | bundleone.js - // | es/ - // | bundleone.js - // | bundletwo.js - // | ...etc - // | ... - // - // Each directory is named for a locale as specified by RFC 3066, - // (http://www.ietf.org/rfc/rfc3066.txt), normalized in lowercase. - // Note that the two bundles in the example do not define all the - // same variants. For a given locale, bundles will be loaded for - // that locale and all more general locales above it, including a - // fallback at the root directory. For example, a declaration for - // the "de-at" locale will first load `nls/de-at/bundleone.js`, - // then `nls/de/bundleone.js` and finally `nls/bundleone.js`. The - // data will be flattened into a single Object so that lookups - // will follow this cascading pattern. An optional build step can - // preload the bundles to avoid data redundancy and the multiple - // network hits normally required to load these resources. - - d.require("dojo.i18n"); - d.i18n._requireLocalization.apply(d.hostenv, arguments); - }; - - - var ore = new RegExp("^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$"); - var ire = new RegExp("^((([^:]+:)?([^@]+))@)?([^:]*)(:([0-9]+))?$"); - - dojo._Url = function(/*dojo._Url||String...*/){ - // summary: - // Constructor to create an object representing a URL. - // It is marked as private, since we might consider removing - // or simplifying it. - // description: - // Each argument is evaluated in order relative to the next until - // a canonical uri is produced. To get an absolute Uri relative to - // the current document use: - // new dojo._Url(document.baseURI, url) - - var n = null; - - // TODO: support for IPv6, see RFC 2732 - var _a = arguments; - var uri = [_a[0]]; - // resolve uri components relative to each other - for(var i = 1; i<_a.length; i++){ - if(!_a[i]){ continue; } - - // Safari doesn't support this.constructor so we have to be explicit - // FIXME: Tracked (and fixed) in Webkit bug 3537. - // http://bugs.webkit.org/show_bug.cgi?id=3537 - var relobj = new d._Url(_a[i]+""); - var uriobj = new d._Url(uri[0]+""); - - if( - relobj.path == "" && - !relobj.scheme && - !relobj.authority && - !relobj.query - ){ - if(relobj.fragment != n){ - uriobj.fragment = relobj.fragment; - } - relobj = uriobj; - }else if(!relobj.scheme){ - relobj.scheme = uriobj.scheme; - - if(!relobj.authority){ - relobj.authority = uriobj.authority; - - if(relobj.path.charAt(0) != "/"){ - var path = uriobj.path.substring(0, - uriobj.path.lastIndexOf("/") + 1) + relobj.path; - - var segs = path.split("/"); - for(var j = 0; j < segs.length; j++){ - if(segs[j] == "."){ - // flatten "./" references - if(j == segs.length - 1){ - segs[j] = ""; - }else{ - segs.splice(j, 1); - j--; - } - }else if(j > 0 && !(j == 1 && segs[0] == "") && - segs[j] == ".." && segs[j-1] != ".."){ - // flatten "../" references - if(j == (segs.length - 1)){ - segs.splice(j, 1); - segs[j - 1] = ""; - }else{ - segs.splice(j - 1, 2); - j -= 2; - } - } - } - relobj.path = segs.join("/"); - } - } - } - - uri = []; - if(relobj.scheme){ - uri.push(relobj.scheme, ":"); - } - if(relobj.authority){ - uri.push("//", relobj.authority); - } - uri.push(relobj.path); - if(relobj.query){ - uri.push("?", relobj.query); - } - if(relobj.fragment){ - uri.push("#", relobj.fragment); - } - } - - this.uri = uri.join(""); - - // break the uri into its main components - var r = this.uri.match(ore); - - this.scheme = r[2] || (r[1] ? "" : n); - this.authority = r[4] || (r[3] ? "" : n); - this.path = r[5]; // can never be undefined - this.query = r[7] || (r[6] ? "" : n); - this.fragment = r[9] || (r[8] ? "" : n); - - if(this.authority != n){ - // server based naming authority - r = this.authority.match(ire); - - this.user = r[3] || n; - this.password = r[4] || n; - this.host = r[5]; - this.port = r[7] || n; - } - } - - dojo._Url.prototype.toString = function(){ return this.uri; }; - - dojo.moduleUrl = function(/*String*/module, /*dojo._Url||String*/url){ - // summary: - // Returns a `dojo._Url` object relative to a module. - // example: - // | var pngPath = dojo.moduleUrl("acme","images/small.png"); - // | console.dir(pngPath); // list the object properties - // | // create an image and set it's source to pngPath's value: - // | var img = document.createElement("img"); - // | // NOTE: we assign the string representation of the url object - // | img.src = pngPath.toString(); - // | // add our image to the document - // | dojo.body().appendChild(img); - // example: - // you may de-reference as far as you like down the package - // hierarchy. This is sometimes handy to avoid lenghty relative - // urls or for building portable sub-packages. In this example, - // the `acme.widget` and `acme.util` directories may be located - // under different roots (see `dojo.registerModulePath`) but the - // the modules which reference them can be unaware of their - // relative locations on the filesystem: - // | // somewhere in a configuration block - // | dojo.registerModulePath("acme.widget", "../../acme/widget"); - // | dojo.registerModulePath("acme.util", "../../util"); - // | - // | // ... - // | - // | // code in a module using acme resources - // | var tmpltPath = dojo.moduleUrl("acme.widget","templates/template.html"); - // | var dataPath = dojo.moduleUrl("acme.util","resources/data.json"); - - var loc = d._getModuleSymbols(module).join('/'); - if(!loc){ return null; } - if(loc.lastIndexOf("/") != loc.length-1){ - loc += "/"; - } - - //If the path is an absolute path (starts with a / or is on another - //domain/xdomain) then don't add the baseUrl. - var colonIndex = loc.indexOf(":"); - if(loc.charAt(0) != "/" && (colonIndex == -1 || colonIndex > loc.indexOf("/"))){ - loc = d.baseUrl + loc; - } - - return new d._Url(loc, url); // String - } -})(); - -/*===== -dojo.isBrowser = { - // example: - // | if(dojo.isBrowser){ ... } -}; - -dojo.isFF = { - // example: - // | if(dojo.isFF > 1){ ... } -}; - -dojo.isIE = { - // example: - // | if(dojo.isIE > 6){ - // | // we are IE7 - // | } -}; - -dojo.isSafari = { - // example: - // | if(dojo.isSafari){ ... } - // example: - // Detect iPhone: - // | if(dojo.isSafari && (navigator.userAgent.indexOf("iPhone") < 0)){ - // | // we are iPhone. iPod touch reports "iPod" above - // | } -}; - -dojo = { - // isBrowser: Boolean - // True if the client is a web-browser - isBrowser: true, - // isFF: Number - // Greater than zero if client is FireFox. 0 otherwise. Corresponds to - // major detected FireFox version (1.5, 2, 3, etc.) - isFF: 2, - // isIE: Number - // Greater than zero if client is MSIE(PC). 0 otherwise. Corresponds to - // major detected IE version (6, 7, 8, etc.) - isIE: 6, - // isKhtml: Number - // Greater than zero if client is a KTHML-derived browser (Konqueror, - // Safari, etc.). 0 otherwise. Corresponds to major detected version. - isKhtml: 0, - // isMozilla: Number - // Greater than zero if client is a Mozilla-based browser (Firefox, - // SeaMonkey). 0 otherwise. Corresponds to major detected version. - isMozilla: 0, - // isOpera: Number - // Greater than zero if client is Opera. 0 otherwise. Corresponds to - // major detected version. - isOpera: 0, - // isSafari: Number - // Greater than zero if client is Safari or iPhone. 0 otherwise. - isSafari: 0 -} -=====*/ - -if(typeof window != 'undefined'){ - dojo.isBrowser = true; - dojo._name = "browser"; - - - // attempt to figure out the path to dojo if it isn't set in the config - (function(){ - var d = dojo; - // this is a scope protection closure. We set browser versions and grab - // the URL we were loaded from here. - - // grab the node we were loaded from - if(document && document.getElementsByTagName){ - var scripts = document.getElementsByTagName("script"); - var rePkg = /dojo(\.xd)?\.js(\W|$)/i; - for(var i = 0; i < scripts.length; i++){ - var src = scripts[i].getAttribute("src"); - if(!src){ continue; } - var m = src.match(rePkg); - if(m){ - // find out where we came from - if(!d.config.baseUrl){ - d.config.baseUrl = src.substring(0, m.index); - } - // and find out if we need to modify our behavior - var cfg = scripts[i].getAttribute("djConfig"); - if(cfg){ - var cfgo = eval("({ "+cfg+" })"); - for(var x in cfgo){ - dojo.config[x] = cfgo[x]; - } - } - break; // "first Dojo wins" - } - } - } - d.baseUrl = d.config.baseUrl; - - // fill in the rendering support information in dojo.render.* - var n = navigator; - var dua = n.userAgent; - var dav = n.appVersion; - var tv = parseFloat(dav); - - d.isOpera = (dua.indexOf("Opera") >= 0) ? tv : 0; - // safari detection derived from: - // http://developer.apple.com/internet/safari/faq.html#anchor2 - // http://developer.apple.com/internet/safari/uamatrix.html - var idx = Math.max(dav.indexOf("WebKit"), dav.indexOf("Safari"), 0); - if(idx){ - // try to grab the explicit Safari version first. If we don't get - // one, look for 419.3+ as the indication that we're on something - // "Safari 3-ish". Lastly, default to "Safari 2" handling. - d.isSafari = parseFloat(dav.split("Version/")[1]) || ( ( parseFloat(dav.substr(idx+7)) >= 419.3 ) ? 3 : 2 ) || 2; - } - d.isAIR = (dua.indexOf("AdobeAIR") >= 0) ? 1 : 0; - d.isKhtml = (dav.indexOf("Konqueror") >= 0 || d.isSafari) ? tv : 0; - d.isMozilla = d.isMoz = (dua.indexOf("Gecko") >= 0 && !d.isKhtml) ? tv : 0; - d.isFF = d.isIE = 0; - if(d.isMoz){ - d.isFF = parseFloat(dua.split("Firefox/")[1]) || 0; - } - if(document.all && !d.isOpera){ - d.isIE = parseFloat(dav.split("MSIE ")[1]) || 0; - } - - //Workaround to get local file loads of dojo to work on IE 7 - //by forcing to not use native xhr. - if(dojo.isIE && window.location.protocol === "file:"){ - dojo.config.ieForceActiveXXhr=true; - } - - var cm = document.compatMode; - d.isQuirks = cm == "BackCompat" || cm == "QuirksMode" || d.isIE < 6; - - // TODO: is the HTML LANG attribute relevant? - d.locale = dojo.config.locale || (d.isIE ? n.userLanguage : n.language).toLowerCase(); - - // These are in order of decreasing likelihood; this will change in time. - d._XMLHTTP_PROGIDS = ['Msxml2.XMLHTTP', 'Microsoft.XMLHTTP', 'Msxml2.XMLHTTP.4.0']; - - d._xhrObj = function(){ - // summary: - // does the work of portably generating a new XMLHTTPRequest - // object. - var http = null; - var last_e = null; - if(!dojo.isIE || !dojo.config.ieForceActiveXXhr){ - try{ http = new XMLHttpRequest(); }catch(e){} - } - if(!http){ - for(var i=0; i<3; ++i){ - var progid = d._XMLHTTP_PROGIDS[i]; - try{ - http = new ActiveXObject(progid); - }catch(e){ - last_e = e; - } - - if(http){ - d._XMLHTTP_PROGIDS = [progid]; // so faster next time - break; - } - } - } - - if(!http){ - throw new Error("XMLHTTP not available: "+last_e); - } - - return http; // XMLHTTPRequest instance - } - - d._isDocumentOk = function(http){ - var stat = http.status || 0; - return (stat >= 200 && stat < 300) || // Boolean - stat == 304 || // allow any 2XX response code - stat == 1223 || // get it out of the cache - (!stat && (location.protocol=="file:" || location.protocol=="chrome:") ); // Internet Explorer mangled the status code - } - - //See if base tag is in use. - //This is to fix http://trac.dojotoolkit.org/ticket/3973, - //but really, we need to find out how to get rid of the dojo._Url reference - //below and still have DOH work with the dojo.i18n test following some other - //test that uses the test frame to load a document (trac #2757). - //Opera still has problems, but perhaps a larger issue of base tag support - //with XHR requests (hasBase is true, but the request is still made to document - //path, not base path). - var owloc = window.location+""; - var base = document.getElementsByTagName("base"); - var hasBase = (base && base.length > 0); - - d._getText = function(/*URI*/ uri, /*Boolean*/ fail_ok){ - // summary: Read the contents of the specified uri and return those contents. - // uri: - // A relative or absolute uri. If absolute, it still must be in - // the same "domain" as we are. - // fail_ok: - // Default false. If fail_ok and loading fails, return null - // instead of throwing. - // returns: The response text. null is returned when there is a - // failure and failure is okay (an exception otherwise) - - // alert("_getText: " + uri); - - // NOTE: must be declared before scope switches ie. this._xhrObj() - var http = this._xhrObj(); - - if(!hasBase && dojo._Url){ - uri = (new dojo._Url(owloc, uri)).toString(); - } - /* - console.debug("_getText:", uri); - console.debug(window.location+""); - alert(uri); - */ - - if(d.config.cacheBust){ - uri += (uri.indexOf("?") == -1 ? "?" : "&") + String(d.config.cacheBust).replace(/\W+/g,""); - } - - http.open('GET', uri, false); - try{ - http.send(null); - // alert(http); - if(!d._isDocumentOk(http)){ - var err = Error("Unable to load "+uri+" status:"+ http.status); - err.status = http.status; - err.responseText = http.responseText; - throw err; - } - }catch(e){ - if(fail_ok){ return null; } // null - // rethrow the exception - throw e; - } - return http.responseText; // String - } - })(); - - dojo._initFired = false; - // BEGIN DOMContentLoaded, from Dean Edwards (http://dean.edwards.name/weblog/2006/06/again/) - dojo._loadInit = function(e){ - dojo._initFired = true; - // allow multiple calls, only first one will take effect - // A bug in khtml calls events callbacks for document for event which isnt supported - // for example a created contextmenu event calls DOMContentLoaded, workaround - var type = (e && e.type) ? e.type.toLowerCase() : "load"; - if(arguments.callee.initialized || (type != "domcontentloaded" && type != "load")){ return; } - arguments.callee.initialized = true; - if("_khtmlTimer" in dojo){ - clearInterval(dojo._khtmlTimer); - delete dojo._khtmlTimer; - } - - if(dojo._inFlightCount == 0){ - dojo._modulesLoaded(); - } - } - - dojo._fakeLoadInit = function(){ - dojo._loadInit({type: "load"}); - } - - if(!dojo.config.afterOnLoad){ - // START DOMContentLoaded - // Mozilla and Opera 9 expose the event we could use - if(document.addEventListener){ - // NOTE: - // due to a threading issue in Firefox 2.0, we can't enable - // DOMContentLoaded on that platform. For more information, see: - // http://trac.dojotoolkit.org/ticket/1704 - if(dojo.isOpera || dojo.isFF >= 3 || (dojo.isMoz && dojo.config.enableMozDomContentLoaded === true)){ - document.addEventListener("DOMContentLoaded", dojo._loadInit, null); - } - - // mainly for Opera 8.5, won't be fired if DOMContentLoaded fired already. - // also used for Mozilla because of trac #1640 - window.addEventListener("load", dojo._loadInit, null); - } - - if(dojo.isAIR){ - window.addEventListener("load", dojo._loadInit, null); - }else if(/(WebKit|khtml)/i.test(navigator.userAgent)){ // sniff - dojo._khtmlTimer = setInterval(function(){ - if(/loaded|complete/.test(document.readyState)){ - dojo._loadInit(); // call the onload handler - } - }, 10); - } - // END DOMContentLoaded - } - - (function(){ - var _w = window; - var _handleNodeEvent = function(/*String*/evtName, /*Function*/fp){ - // summary: - // non-destructively adds the specified function to the node's - // evtName handler. - // evtName: should be in the form "onclick" for "onclick" handlers. - // Make sure you pass in the "on" part. - var oldHandler = _w[evtName] || function(){}; - _w[evtName] = function(){ - fp.apply(_w, arguments); - oldHandler.apply(_w, arguments); - }; - }; - - if(dojo.isIE){ - // for Internet Explorer. readyState will not be achieved on init - // call, but dojo doesn't need it however, we'll include it - // because we don't know if there are other functions added that - // might. Note that this has changed because the build process - // strips all comments -- including conditional ones. - if(!dojo.config.afterOnLoad){ - document.write('<scr'+'ipt defer src="//:" ' - + 'onreadystatechange="if(this.readyState==\'complete\'){' + dojo._scopeName + '._loadInit();}">' - + '</scr'+'ipt>' - ); - } - - // IE WebControl hosted in an application can fire "beforeunload" and "unload" - // events when control visibility changes, causing Dojo to unload too soon. The - // following code fixes the problem - // Reference: http://support.microsoft.com/default.aspx?scid=kb;en-us;199155 - var _unloading = true; - _handleNodeEvent("onbeforeunload", function(){ - _w.setTimeout(function(){ _unloading = false; }, 0); - }); - _handleNodeEvent("onunload", function(){ - if(_unloading){ dojo.unloaded(); } - }); - - try{ - document.namespaces.add("v","urn:schemas-microsoft-com:vml"); - document.createStyleSheet().addRule("v\\:*", "behavior:url(#default#VML)"); - }catch(e){} - }else{ - // FIXME: dojo.unloaded requires dojo scope, so using anon function wrapper. - _handleNodeEvent("onbeforeunload", function() { dojo.unloaded(); }); - } - - })(); - - /* - OpenAjax.subscribe("OpenAjax", "onload", function(){ - if(dojo._inFlightCount == 0){ - dojo._modulesLoaded(); - } - }); - - OpenAjax.subscribe("OpenAjax", "onunload", function(){ - dojo.unloaded(); - }); - */ -} //if (typeof window != 'undefined') - -//Register any module paths set up in djConfig. Need to do this -//in the hostenvs since hostenv_browser can read djConfig from a -//script tag's attribute. -(function(){ - var mp = dojo.config["modulePaths"]; - if(mp){ - for(var param in mp){ - dojo.registerModulePath(param, mp[param]); - } - } -})(); - -//Load debug code if necessary. -if(dojo.config.isDebug){ - dojo.require("dojo._firebug.firebug"); -} - -if(dojo.config.debugAtAllCosts){ - dojo.config.useXDomain = true; - dojo.require("dojo._base._loader.loader_xd"); - dojo.require("dojo._base._loader.loader_debug"); - dojo.require("dojo.i18n"); -} - -if(!dojo._hasResource["dojo._base.lang"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.lang"] = true; -dojo.provide("dojo._base.lang"); - -// Crockford (ish) functions - -dojo.isString = function(/*anything*/ it){ - // summary: - // Return true if it is a String - return !!arguments.length && it != null && (typeof it == "string" || it instanceof String); // Boolean -} - -dojo.isArray = function(/*anything*/ it){ - // summary: - // Return true if it is an Array - return it && (it instanceof Array || typeof it == "array"); // Boolean -} - -/*===== -dojo.isFunction = function(it){ - // summary: Return true if it is a Function - // it: anything - // return: Boolean -} -=====*/ - -dojo.isFunction = (function(){ - var _isFunction = function(/*anything*/ it){ - return it && (typeof it == "function" || it instanceof Function); // Boolean - }; - - return dojo.isSafari ? - // only slow this down w/ gratuitious casting in Safari since it's what's b0rken - function(/*anything*/ it){ - if(typeof it == "function" && it == "[object NodeList]"){ return false; } - return _isFunction(it); // Boolean - } : _isFunction; -})(); - -dojo.isObject = function(/*anything*/ it){ - // summary: - // Returns true if it is a JavaScript object (or an Array, a Function - // or null) - return it !== undefined && - (it === null || typeof it == "object" || dojo.isArray(it) || dojo.isFunction(it)); // Boolean -} - -dojo.isArrayLike = function(/*anything*/ it){ - // summary: - // similar to dojo.isArray() but more permissive - // description: - // Doesn't strongly test for "arrayness". Instead, settles for "isn't - // a string or number and has a length property". Arguments objects - // and DOM collections will return true when passed to - // dojo.isArrayLike(), but will return false when passed to - // dojo.isArray(). - // return: - // If it walks like a duck and quicks like a duck, return `true` - var d = dojo; - return it && it !== undefined && - // keep out built-in constructors (Number, String, ...) which have length - // properties - !d.isString(it) && !d.isFunction(it) && - !(it.tagName && it.tagName.toLowerCase() == 'form') && - (d.isArray(it) || isFinite(it.length)); // Boolean -} - -dojo.isAlien = function(/*anything*/ it){ - // summary: - // Returns true if it is a built-in function or some other kind of - // oddball that *should* report as a function but doesn't - return it && !dojo.isFunction(it) && /\{\s*\[native code\]\s*\}/.test(String(it)); // Boolean -} - -dojo.extend = function(/*Object*/ constructor, /*Object...*/ props){ - // summary: - // Adds all properties and methods of props to constructor's - // prototype, making them available to all instances created with - // constructor. - for(var i=1, l=arguments.length; i<l; i++){ - dojo._mixin(constructor.prototype, arguments[i]); - } - return constructor; // Object -} - -dojo._hitchArgs = function(scope, method /*,...*/){ - var pre = dojo._toArray(arguments, 2); - var named = dojo.isString(method); - return function(){ - // arrayify arguments - var args = dojo._toArray(arguments); - // locate our method - var f = named ? (scope||dojo.global)[method] : method; - // invoke with collected args - return f && f.apply(scope || this, pre.concat(args)); // mixed - } // Function -} - -dojo.hitch = function(/*Object*/scope, /*Function|String*/method /*,...*/){ - // summary: - // Returns a function that will only ever execute in the a given scope. - // This allows for easy use of object member functions - // in callbacks and other places in which the "this" keyword may - // otherwise not reference the expected scope. - // Any number of default positional arguments may be passed as parameters - // beyond "method". - // Each of these values will be used to "placehold" (similar to curry) - // for the hitched function. - // scope: - // The scope to use when method executes. If method is a string, - // scope is also the object containing method. - // method: - // A function to be hitched to scope, or the name of the method in - // scope to be hitched. - // example: - // | dojo.hitch(foo, "bar")(); - // runs foo.bar() in the scope of foo - // example: - // | dojo.hitch(foo, myFunction); - // returns a function that runs myFunction in the scope of foo - if(arguments.length > 2){ - return dojo._hitchArgs.apply(dojo, arguments); // Function - } - if(!method){ - method = scope; - scope = null; - } - if(dojo.isString(method)){ - scope = scope || dojo.global; - if(!scope[method]){ throw(['dojo.hitch: scope["', method, '"] is null (scope="', scope, '")'].join('')); } - return function(){ return scope[method].apply(scope, arguments || []); }; // Function - } - return !scope ? method : function(){ return method.apply(scope, arguments || []); }; // Function -} - -/*===== -dojo.delegate = function(obj, props){ - // summary: - // returns a new object which "looks" to obj for properties which it - // does not have a value for. Optionally takes a bag of properties to - // seed the returned object with initially. - // description: - // This is a small implementaton of the Boodman/Crockford delegation - // pattern in JavaScript. An intermediate object constructor mediates - // the prototype chain for the returned object, using it to delegate - // down to obj for property lookup when object-local lookup fails. - // This can be thought of similarly to ES4's "wrap", save that it does - // not act on types but rather on pure objects. - // obj: - // The object to delegate to for properties not found directly on the - // return object or in props. - // props: - // an object containing properties to assign to the returned object - // returns: - // an Object of anonymous type - // example: - // | var foo = { bar: "baz" }; - // | var thinger = dojo.delegate(foo, { thud: "xyzzy"}); - // | thinger.bar == "baz"; // delegated to foo - // | foo.thud == undefined; // by definition - // | thinger.thud == "xyzzy"; // mixed in from props - // | foo.bar = "thonk"; - // | thinger.bar == "thonk"; // still delegated to foo's bar -} -=====*/ - - -dojo.delegate = dojo._delegate = function(obj, props){ - - // boodman/crockford delegation - function TMP(){}; - TMP.prototype = obj; - var tmp = new TMP(); - if(props){ - dojo.mixin(tmp, props); - } - return tmp; // Object -} - -dojo.partial = function(/*Function|String*/method /*, ...*/){ - // summary: - // similar to hitch() except that the scope object is left to be - // whatever the execution context eventually becomes. - // description: - // Calling dojo.partial is the functional equivalent of calling: - // | dojo.hitch(null, funcName, ...); - var arr = [ null ]; - return dojo.hitch.apply(dojo, arr.concat(dojo._toArray(arguments))); // Function -} - -dojo._toArray = function(/*Object*/obj, /*Number?*/offset, /*Array?*/ startWith){ - // summary: - // Converts an array-like object (i.e. arguments, DOMCollection) to an - // array. Returns a new Array with the elements of obj. - // obj: - // the object to "arrayify". We expect the object to have, at a - // minimum, a length property which corresponds to integer-indexed - // properties. - // offset: - // the location in obj to start iterating from. Defaults to 0. - // Optional. - // startWith: - // An array to pack with the properties of obj. If provided, - // properties in obj are appended at the end of startWith and - // startWith is the returned array. - var arr = startWith||[]; - for(var x = offset || 0; x < obj.length; x++){ - arr.push(obj[x]); - } - return arr; // Array -} - -dojo.clone = function(/*anything*/ o){ - // summary: - // Clones objects (including DOM nodes) and all children. - // Warning: do not clone cyclic structures. - if(!o){ return o; } - if(dojo.isArray(o)){ - var r = []; - for(var i = 0; i < o.length; ++i){ - r.push(dojo.clone(o[i])); - } - return r; // Array - } - if(!dojo.isObject(o)){ - return o; /*anything*/ - } - if(o.nodeType && o.cloneNode){ // isNode - return o.cloneNode(true); // Node - } - if(o instanceof Date){ - return new Date(o.getTime()); // Date - } - // Generic objects - var r = new o.constructor(); // specific to dojo.declare()'d classes! - for(var i in o){ - if(!(i in r) || r[i] != o[i]){ - r[i] = dojo.clone(o[i]); - } - } - return r; // Object -} - -dojo.trim = function(/*String*/ str){ - // summary: - // trims whitespaces from both sides of the string - // description: - // This version of trim() was selected for inclusion into the base due - // to its compact size and relatively good performance (see Steven - // Levithan's blog: - // http://blog.stevenlevithan.com/archives/faster-trim-javascript). - // The fastest but longest version of this function is located at - // dojo.string.trim() - return str.replace(/^\s\s*/, '').replace(/\s\s*$/, ''); // String -} - -} - -if(!dojo._hasResource["dojo._base.declare"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.declare"] = true; -dojo.provide("dojo._base.declare"); - - -// this file courtesy of the TurboAjax group, licensed under a Dojo CLA - -dojo.declare = function(/*String*/ className, /*Function|Function[]*/ superclass, /*Object*/ props){ - // summary: - // Create a feature-rich constructor from compact notation - // className: - // The name of the constructor (loosely, a "class") - // stored in the "declaredClass" property in the created prototype - // superclass: - // May be null, a Function, or an Array of Functions. If an array, - // the first element is used as the prototypical ancestor and - // any following Functions become mixin ancestors. - // props: - // An object whose properties are copied to the - // created prototype. - // Add an instance-initialization function by making it a property - // named "constructor". - // description: - // Create a constructor using a compact notation for inheritance and - // prototype extension. - // - // All superclasses (including mixins) must be Functions (not simple Objects). - // - // Mixin ancestors provide a type of multiple inheritance. Prototypes of mixin - // ancestors are copied to the new class: changes to mixin prototypes will - // not affect classes to which they have been mixed in. - // - // "className" is cached in "declaredClass" property of the new class. - // - // example: - // | dojo.declare("my.classes.bar", my.classes.foo, { - // | // properties to be added to the class prototype - // | someValue: 2, - // | // initialization function - // | constructor: function(){ - // | this.myComplicatedObject = new ReallyComplicatedObject(); - // | }, - // | // other functions - // | someMethod: function(){ - // | doStuff(); - // | } - // | ); - - // process superclass argument - // var dd=dojo.declare, mixins=null; - var dd = arguments.callee, mixins; - if(dojo.isArray(superclass)){ - mixins = superclass; - superclass = mixins.shift(); - } - // construct intermediate classes for mixins - if(mixins){ - dojo.forEach(mixins, function(m){ - if(!m){ throw(className + ": mixin #" + i + " is null"); } // It's likely a required module is not loaded - superclass = dd._delegate(superclass, m); - }); - } - // prepare values - var init = (props||0).constructor, ctor = dd._delegate(superclass), fn; - // name methods (experimental) - for(var i in props){ if(dojo.isFunction(fn = props[i]) && !0[i]){fn.nom = i;} } // 0[i] checks Object.prototype - // decorate prototype - dojo.extend(ctor, {declaredClass: className, _constructor: init, preamble: null}, props || 0); - // special help for IE - ctor.prototype.constructor = ctor; - // create named reference - return dojo.setObject(className, ctor); // Function -}; - -dojo.mixin(dojo.declare, { - _delegate: function(base, mixin){ - var bp = (base||0).prototype, mp = (mixin||0).prototype; - // fresh constructor, fresh prototype - var ctor = dojo.declare._makeCtor(); - // cache ancestry - dojo.mixin(ctor, {superclass: bp, mixin: mp, extend: dojo.declare._extend}); - // chain prototypes - if(base){ctor.prototype = dojo._delegate(bp);} - // add mixin and core - dojo.extend(ctor, dojo.declare._core, mp||0, {_constructor: null, preamble: null}); - // special help for IE - ctor.prototype.constructor = ctor; - // name this class for debugging - ctor.prototype.declaredClass = (bp||0).declaredClass + '_' + (mp||0).declaredClass; - return ctor; - }, - _extend: function(props){ - for(var i in props){ if(dojo.isFunction(fn=props[i]) && !0[i]){fn.nom=i;} } - dojo.extend(this, props); - }, - _makeCtor: function(){ - // we have to make a function, but don't want to close over anything - return function(){ this._construct(arguments); }; - }, - _core: { - _construct: function(args){ - var c=args.callee, s=c.superclass, ct=s&&s.constructor, m=c.mixin, mct=m&&m.constructor, a=args, ii, fn; - // side-effect of = used on purpose here, lint may complain, don't try this at home - if(a[0]){ - // FIXME: preambles for each mixin should be allowed - // FIXME: - // should we allow the preamble here NOT to modify the - // default args, but instead to act on each mixin - // independently of the class instance being constructed - // (for impedence matching)? - - // allow any first argument w/ a "preamble" property to act as a - // class preamble (not exclusive of the prototype preamble) - if(/*dojo.isFunction*/((fn = a[0].preamble))){ - a = fn.apply(this, a) || a; - } - } - // prototype preamble - if((fn = c.prototype.preamble)){a = fn.apply(this, a) || a;} - // FIXME: - // need to provide an optional prototype-settable - // "_explicitSuper" property which disables this - // initialize superclass - if(ct&&ct.apply){ct.apply(this, a);} - // initialize mixin - if(mct&&mct.apply){mct.apply(this, a);} - // initialize self - if((ii=c.prototype._constructor)){ii.apply(this, args);} - // post construction - if(this.constructor.prototype==c.prototype && (ct=this.postscript)){ ct.apply(this, args); } - }, - _findMixin: function(mixin){ - var c = this.constructor, p, m; - while(c){ - p = c.superclass; - m = c.mixin; - if(m==mixin || (m instanceof mixin.constructor)){return p;} - if(m && (m=m._findMixin(mixin))){return m;} - c = p && p.constructor; - } - }, - _findMethod: function(name, method, ptype, has){ - // consciously trading readability for bytes and speed in this low-level method - var p=ptype, c, m, f; - do{ - c = p.constructor; - m = c.mixin; - // find method by name in our mixin ancestor - if(m && (m=this._findMethod(name, method, m, has))){return m;} - // if we found a named method that either exactly-is or exactly-is-not 'method' - if((f=p[name])&&(has==(f==method))){return p;} - // ascend chain - p = c.superclass; - }while(p); - // if we couldn't find an ancestor in our primary chain, try a mixin chain - return !has && (p=this._findMixin(ptype)) && this._findMethod(name, method, p, has); - }, - inherited: function(name, args, newArgs){ - // optionalize name argument (experimental) - var a = arguments; - if(!dojo.isString(a[0])){newArgs=args; args=name; name=args.callee.nom;} - a = newArgs||args; - var c = args.callee, p = this.constructor.prototype, fn, mp; - // if not an instance override - if(this[name] != c || p[name] == c){ - mp = this._findMethod(name, c, p, true); - if(!mp){throw(this.declaredClass + ': inherited method "' + name + '" mismatch');} - p = this._findMethod(name, c, mp, false); - } - fn = p && p[name]; - if(!fn){throw(mp.declaredClass + ': inherited method "' + name + '" not found');} - // if the function exists, invoke it in our scope - return fn.apply(this, a); - } - } -}); - -} - -if(!dojo._hasResource["dojo._base.connect"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.connect"] = true; -dojo.provide("dojo._base.connect"); - - -// this file courtesy of the TurboAjax Group, licensed under a Dojo CLA - -// low-level delegation machinery -dojo._listener = { - // create a dispatcher function - getDispatcher: function(){ - // following comments pulled out-of-line to prevent cloning them - // in the returned function. - // - indices (i) that are really in the array of listeners (ls) will - // not be in Array.prototype. This is the 'sparse array' trick - // that keeps us safe from libs that take liberties with built-in - // objects - // - listener is invoked with current scope (this) - return function(){ - var ap=Array.prototype, c=arguments.callee, ls=c._listeners, t=c.target; - // return value comes from original target function - var r=t && t.apply(this, arguments); - // invoke listeners after target function - for(var i in ls){ - if(!(i in ap)){ - ls[i].apply(this, arguments); - } - } - // return value comes from original target function - return r; - } - }, - // add a listener to an object - add: function(/*Object*/ source, /*String*/ method, /*Function*/ listener){ - // Whenever 'method' is invoked, 'listener' will have the same scope. - // Trying to supporting a context object for the listener led to - // complexity. - // Non trivial to provide 'once' functionality here - // because listener could be the result of a dojo.hitch call, - // in which case two references to the same hitch target would not - // be equivalent. - source = source || dojo.global; - // The source method is either null, a dispatcher, or some other function - var f = source[method]; - // Ensure a dispatcher - if(!f||!f._listeners){ - var d = dojo._listener.getDispatcher(); - // original target function is special - d.target = f; - // dispatcher holds a list of listeners - d._listeners = []; - // redirect source to dispatcher - f = source[method] = d; - } - // The contract is that a handle is returned that can - // identify this listener for disconnect. - // - // The type of the handle is private. Here is it implemented as Integer. - // DOM event code has this same contract but handle is Function - // in non-IE browsers. - // - // We could have separate lists of before and after listeners. - return f._listeners.push(listener) ; /*Handle*/ - }, - // remove a listener from an object - remove: function(/*Object*/ source, /*String*/ method, /*Handle*/ handle){ - var f = (source||dojo.global)[method]; - // remember that handle is the index+1 (0 is not a valid handle) - if(f && f._listeners && handle--){ - delete f._listeners[handle]; - } - } -}; - -// Multiple delegation for arbitrary methods. - -// This unit knows nothing about DOM, -// but we include DOM aware -// documentation and dontFix -// argument here to help the autodocs. -// Actual DOM aware code is in event.js. - -dojo.connect = function(/*Object|null*/ obj, - /*String*/ event, - /*Object|null*/ context, - /*String|Function*/ method, - /*Boolean*/ dontFix){ - // summary: - // Create a link that calls one function when another executes. - // - // description: - // Connects method to event, so that after event fires, method - // does too. All connected functions are passed the same arguments as - // the event function was initially called with. You may connect as - // many methods to event as needed. - // - // event must be a string. If obj is null, dojo.global is used. - // - // null arguments may simply be omitted. - // - // obj[event] can resolve to a function or undefined (null). - // If obj[event] is null, it is assigned a function. - // - // The return value is a handle that is needed to - // remove this connection with dojo.disconnect. - // - // obj: - // The source object for the event function. - // Defaults to dojo.global if null. - // If obj is a DOM node, the connection is delegated - // to the DOM event manager (unless dontFix is true). - // - // event: - // String name of the event function in obj. - // I.e. identifies a property obj[event]. - // - // context: - // The object that method will receive as "this". - // - // If context is null and method is a function, then method - // inherits the context of event. - // - // If method is a string then context must be the source - // object object for method (context[method]). If context is null, - // dojo.global is used. - // - // method: - // A function reference, or name of a function in context. - // The function identified by method fires after event does. - // method receives the same arguments as the event. - // See context argument comments for information on method's scope. - // - // dontFix: - // If obj is a DOM node, set dontFix to true to prevent delegation - // of this connection to the DOM event manager. - // - // example: - // When obj.onchange(), do ui.update(): - // | dojo.connect(obj, "onchange", ui, "update"); - // | dojo.connect(obj, "onchange", ui, ui.update); // same - // - // example: - // Using return value for disconnect: - // | var link = dojo.connect(obj, "onchange", ui, "update"); - // | ... - // | dojo.disconnect(link); - // - // example: - // When onglobalevent executes, watcher.handler is invoked: - // | dojo.connect(null, "onglobalevent", watcher, "handler"); - // - // example: - // When ob.onCustomEvent executes, customEventHandler is invoked: - // | dojo.connect(ob, "onCustomEvent", null, "customEventHandler"); - // | dojo.connect(ob, "onCustomEvent", "customEventHandler"); // same - // - // example: - // When ob.onCustomEvent executes, customEventHandler is invoked - // with the same scope (this): - // | dojo.connect(ob, "onCustomEvent", null, customEventHandler); - // | dojo.connect(ob, "onCustomEvent", customEventHandler); // same - // - // example: - // When globalEvent executes, globalHandler is invoked - // with the same scope (this): - // | dojo.connect(null, "globalEvent", null, globalHandler); - // | dojo.connect("globalEvent", globalHandler); // same - - // normalize arguments - var a=arguments, args=[], i=0; - // if a[0] is a String, obj was ommited - args.push(dojo.isString(a[0]) ? null : a[i++], a[i++]); - // if the arg-after-next is a String or Function, context was NOT omitted - var a1 = a[i+1]; - args.push(dojo.isString(a1)||dojo.isFunction(a1) ? a[i++] : null, a[i++]); - // absorb any additional arguments - for(var l=a.length; i<l; i++){ args.push(a[i]); } - // do the actual work - return dojo._connect.apply(this, args); /*Handle*/ -} - -// used by non-browser hostenvs. always overriden by event.js -dojo._connect = function(obj, event, context, method){ - var l=dojo._listener, h=l.add(obj, event, dojo.hitch(context, method)); - return [obj, event, h, l]; // Handle -} - -dojo.disconnect = function(/*Handle*/ handle){ - // summary: - // Remove a link created by dojo.connect. - // description: - // Removes the connection between event and the method referenced by handle. - // handle: - // the return value of the dojo.connect call that created the connection. - if(handle && handle[0] !== undefined){ - dojo._disconnect.apply(this, handle); - // let's not keep this reference - delete handle[0]; - } -} - -dojo._disconnect = function(obj, event, handle, listener){ - listener.remove(obj, event, handle); -} - -// topic publish/subscribe - -dojo._topics = {}; - -dojo.subscribe = function(/*String*/ topic, /*Object|null*/ context, /*String|Function*/ method){ - // summary: - // Attach a listener to a named topic. The listener function is invoked whenever the - // named topic is published (see: dojo.publish). - // Returns a handle which is needed to unsubscribe this listener. - // context: - // Scope in which method will be invoked, or null for default scope. - // method: - // The name of a function in context, or a function reference. This is the function that - // is invoked when topic is published. - // example: - // | dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }; - // | dojo.publish("alerts", [ "read this", "hello world" ]); - - // support for 2 argument invocation (omitting context) depends on hitch - return [topic, dojo._listener.add(dojo._topics, topic, dojo.hitch(context, method))]; /*Handle*/ -} - -dojo.unsubscribe = function(/*Handle*/ handle){ - // summary: - // Remove a topic listener. - // handle: - // The handle returned from a call to subscribe. - // example: - // | var alerter = dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }; - // | ... - // | dojo.unsubscribe(alerter); - if(handle){ - dojo._listener.remove(dojo._topics, handle[0], handle[1]); - } -} - -dojo.publish = function(/*String*/ topic, /*Array*/ args){ - // summary: - // Invoke all listener method subscribed to topic. - // topic: - // The name of the topic to publish. - // args: - // An array of arguments. The arguments will be applied - // to each topic subscriber (as first class parameters, via apply). - // example: - // | dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }; - // | dojo.publish("alerts", [ "read this", "hello world" ]); - - // Note that args is an array, which is more efficient vs variable length - // argument list. Ideally, var args would be implemented via Array - // throughout the APIs. - var f = dojo._topics[topic]; - if(f){ - f.apply(this, args||[]); - } -} - -dojo.connectPublisher = function( /*String*/ topic, - /*Object|null*/ obj, - /*String*/ event){ - // summary: - // Ensure that everytime obj.event() is called, a message is published - // on the topic. Returns a handle which can be passed to - // dojo.disconnect() to disable subsequent automatic publication on - // the topic. - // topic: - // The name of the topic to publish. - // obj: - // The source object for the event function. Defaults to dojo.global - // if null. - // event: - // The name of the event function in obj. - // I.e. identifies a property obj[event]. - // example: - // | dojo.connectPublisher("/ajax/start", dojo, "xhrGet"}; - var pf = function(){ dojo.publish(topic, arguments); } - return (event) ? dojo.connect(obj, event, pf) : dojo.connect(obj, pf); //Handle -}; - -} - -if(!dojo._hasResource["dojo._base.Deferred"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.Deferred"] = true; -dojo.provide("dojo._base.Deferred"); - - -dojo.Deferred = function(/*Function?*/ canceller){ - // summary: - // Encapsulates a sequence of callbacks in response to a value that - // may not yet be available. This is modeled after the Deferred class - // from Twisted <http://twistedmatrix.com>. - // description: - // JavaScript has no threads, and even if it did, threads are hard. - // Deferreds are a way of abstracting non-blocking events, such as the - // final response to an XMLHttpRequest. Deferreds create a promise to - // return a response a some point in the future and an easy way to - // register your interest in receiving that response. - // - // The most important methods for Deffered users are: - // - // * addCallback(handler) - // * addErrback(handler) - // * callback(result) - // * errback(result) - // - // In general, when a function returns a Deferred, users then "fill - // in" the second half of the contract by registering callbacks and - // error handlers. You may register as many callback and errback - // handlers as you like and they will be executed in the order - // registered when a result is provided. Usually this result is - // provided as the result of an asynchronous operation. The code - // "managing" the Deferred (the code that made the promise to provide - // an answer later) will use the callback() and errback() methods to - // communicate with registered listeners about the result of the - // operation. At this time, all registered result handlers are called - // *with the most recent result value*. - // - // Deferred callback handlers are treated as a chain, and each item in - // the chain is required to return a value that will be fed into - // successive handlers. The most minimal callback may be registered - // like this: - // - // | var d = new dojo.Deferred(); - // | d.addCallback(function(result){ return result; }); - // - // Perhaps the most common mistake when first using Deferreds is to - // forget to return a value (in most cases, the value you were - // passed). - // - // The sequence of callbacks is internally represented as a list of - // 2-tuples containing the callback/errback pair. For example, the - // following call sequence: - // - // | var d = new dojo.Deferred(); - // | d.addCallback(myCallback); - // | d.addErrback(myErrback); - // | d.addBoth(myBoth); - // | d.addCallbacks(myCallback, myErrback); - // - // is translated into a Deferred with the following internal - // representation: - // - // | [ - // | [myCallback, null], - // | [null, myErrback], - // | [myBoth, myBoth], - // | [myCallback, myErrback] - // | ] - // - // The Deferred also keeps track of its current status (fired). Its - // status may be one of three things: - // - // * -1: no value yet (initial condition) - // * 0: success - // * 1: error - // - // A Deferred will be in the error state if one of the following three - // conditions are met: - // - // 1. The result given to callback or errback is "instanceof" Error - // 2. The previous callback or errback raised an exception while - // executing - // 3. The previous callback or errback returned a value - // "instanceof" Error - // - // Otherwise, the Deferred will be in the success state. The state of - // the Deferred determines the next element in the callback sequence - // to run. - // - // When a callback or errback occurs with the example deferred chain, - // something equivalent to the following will happen (imagine - // that exceptions are caught and returned): - // - // | // d.callback(result) or d.errback(result) - // | if(!(result instanceof Error)){ - // | result = myCallback(result); - // | } - // | if(result instanceof Error){ - // | result = myErrback(result); - // | } - // | result = myBoth(result); - // | if(result instanceof Error){ - // | result = myErrback(result); - // | }else{ - // | result = myCallback(result); - // | } - // - // The result is then stored away in case another step is added to the - // callback sequence. Since the Deferred already has a value - // available, any new callbacks added will be called immediately. - // - // There are two other "advanced" details about this implementation - // that are useful: - // - // Callbacks are allowed to return Deferred instances themselves, so - // you can build complicated sequences of events with ease. - // - // The creator of the Deferred may specify a canceller. The canceller - // is a function that will be called if Deferred.cancel is called - // before the Deferred fires. You can use this to implement clean - // aborting of an XMLHttpRequest, etc. Note that cancel will fire the - // deferred with a CancelledError (unless your canceller returns - // another kind of error), so the errbacks should be prepared to - // handle that error for cancellable Deferreds. - // example: - // | var deferred = new dojo.Deferred(); - // | setTimeout(function(){ deferred.callback({success: true}); }, 1000); - // | return deferred; - // example: - // Deferred objects are often used when making code asynchronous. It - // may be easiest to write functions in a synchronous manner and then - // split code using a deferred to trigger a response to a long-lived - // operation. For example, instead of register a callback function to - // denote when a rendering operation completes, the function can - // simply return a deferred: - // - // | // callback style: - // | function renderLotsOfData(data, callback){ - // | var success = false - // | try{ - // | for(var x in data){ - // | renderDataitem(data[x]); - // | } - // | success = true; - // | }catch(e){ } - // | if(callback){ - // | callback(success); - // | } - // | } - // - // | // using callback style - // | renderLotsOfData(someDataObj, function(success){ - // | // handles success or failure - // | if(!success){ - // | promptUserToRecover(); - // | } - // | }); - // | // NOTE: no way to add another callback here!! - // example: - // Using a Deferred doesn't simplify the sending code any, but it - // provides a standard interface for callers and senders alike, - // providing both with a simple way to service multiple callbacks for - // an operation and freeing both sides from worrying about details - // such as "did this get called already?". With Deferreds, new - // callbacks can be added at any time. - // - // | // Deferred style: - // | function renderLotsOfData(data){ - // | var d = new dojo.Deferred(); - // | try{ - // | for(var x in data){ - // | renderDataitem(data[x]); - // | } - // | d.callback(true); - // | }catch(e){ - // | d.errback(new Error("rendering failed")); - // | } - // | return d; - // | } - // - // | // using Deferred style - // | renderLotsOfData(someDataObj).addErrback(function(){ - // | promptUserToRecover(); - // | }); - // | // NOTE: addErrback and addCallback both return the Deferred - // | // again, so we could chain adding callbacks or save the - // | // deferred for later should we need to be notified again. - // example: - // In this example, renderLotsOfData is syncrhonous and so both - // versions are pretty artificial. Putting the data display on a - // timeout helps show why Deferreds rock: - // - // | // Deferred style and async func - // | function renderLotsOfData(data){ - // | var d = new dojo.Deferred(); - // | setTimeout(function(){ - // | try{ - // | for(var x in data){ - // | renderDataitem(data[x]); - // | } - // | d.callback(true); - // | }catch(e){ - // | d.errback(new Error("rendering failed")); - // | } - // | }, 100); - // | return d; - // | } - // - // | // using Deferred style - // | renderLotsOfData(someDataObj).addErrback(function(){ - // | promptUserToRecover(); - // | }); - // - // Note that the caller doesn't have to change his code at all to - // handle the asynchronous case. - - this.chain = []; - this.id = this._nextId(); - this.fired = -1; - this.paused = 0; - this.results = [null, null]; - this.canceller = canceller; - this.silentlyCancelled = false; -}; - -dojo.extend(dojo.Deferred, { - /* - makeCalled: function(){ - // summary: - // returns a new, empty deferred, which is already in the called - // state. Calling callback() or errback() on this deferred will - // yeild an error and adding new handlers to it will result in - // them being called immediately. - var deferred = new dojo.Deferred(); - deferred.callback(); - return deferred; - }, - - toString: function(){ - var state; - if(this.fired == -1){ - state = 'unfired'; - }else{ - state = this.fired ? 'success' : 'error'; - } - return 'Deferred(' + this.id + ', ' + state + ')'; - }, - */ - - _nextId: (function(){ - var n = 1; - return function(){ return n++; }; - })(), - - cancel: function(){ - // summary: - // Cancels a Deferred that has not yet received a value, or is - // waiting on another Deferred as its value. - // description: - // If a canceller is defined, the canceller is called. If the - // canceller did not return an error, or there was no canceller, - // then the errback chain is started. - var err; - if(this.fired == -1){ - if(this.canceller){ - err = this.canceller(this); - }else{ - this.silentlyCancelled = true; - } - if(this.fired == -1){ - if(!(err instanceof Error)){ - var res = err; - err = new Error("Deferred Cancelled"); - err.dojoType = "cancel"; - err.cancelResult = res; - } - this.errback(err); - } - }else if( (this.fired == 0) && - (this.results[0] instanceof dojo.Deferred) - ){ - this.results[0].cancel(); - } - }, - - - _resback: function(res){ - // summary: - // The private primitive that means either callback or errback - this.fired = ((res instanceof Error) ? 1 : 0); - this.results[this.fired] = res; - this._fire(); - }, - - _check: function(){ - if(this.fired != -1){ - if(!this.silentlyCancelled){ - throw new Error("already called!"); - } - this.silentlyCancelled = false; - return; - } - }, - - callback: function(res){ - // summary: - // Begin the callback sequence with a non-error value. - - /* - callback or errback should only be called once on a given - Deferred. - */ - this._check(); - this._resback(res); - }, - - errback: function(/*Error*/res){ - // summary: - // Begin the callback sequence with an error result. - this._check(); - if(!(res instanceof Error)){ - res = new Error(res); - } - this._resback(res); - }, - - addBoth: function(/*Function|Object*/cb, /*String?*/cbfn){ - // summary: - // Add the same function as both a callback and an errback as the - // next element on the callback sequence.This is useful for code - // that you want to guarantee to run, e.g. a finalizer. - var enclosed = dojo.hitch.apply(dojo, arguments); - return this.addCallbacks(enclosed, enclosed); - }, - - addCallback: function(/*Function|Object*/cb, /*String?*/cbfn /*...*/){ - // summary: - // Add a single callback to the end of the callback sequence. - return this.addCallbacks(dojo.hitch.apply(dojo, arguments)); - }, - - addErrback: function(cb, cbfn){ - // summary: - // Add a single callback to the end of the callback sequence. - return this.addCallbacks(null, dojo.hitch.apply(dojo, arguments)); - }, - - addCallbacks: function(cb, eb){ - // summary: - // Add separate callback and errback to the end of the callback - // sequence. - this.chain.push([cb, eb]) - if(this.fired >= 0){ - this._fire(); - } - return this; - }, - - _fire: function(){ - // summary: - // Used internally to exhaust the callback sequence when a result - // is available. - var chain = this.chain; - var fired = this.fired; - var res = this.results[fired]; - var self = this; - var cb = null; - while( - (chain.length > 0) && - (this.paused == 0) - ){ - // Array - var f = chain.shift()[fired]; - if(!f){ continue; } - try{ - res = f(res); - fired = ((res instanceof Error) ? 1 : 0); - if(res instanceof dojo.Deferred){ - cb = function(res){ - self._resback(res); - // inlined from _pause() - self.paused--; - if( - (self.paused == 0) && - (self.fired >= 0) - ){ - self._fire(); - } - } - // inlined from _unpause - this.paused++; - } - }catch(err){ - console.debug(err); - fired = 1; - res = err; - } - } - this.fired = fired; - this.results[fired] = res; - if((cb)&&(this.paused)){ - // this is for "tail recursion" in case the dependent - // deferred is already fired - res.addBoth(cb); - } - } -}); - -} - -if(!dojo._hasResource["dojo._base.json"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.json"] = true; -dojo.provide("dojo._base.json"); - -dojo.fromJson = function(/*String*/ json){ - // summary: - // Parses a [JSON](http://json.org) string to return a JavaScript object. - // json: - // a string literal of a JSON item, for instance: - // `'{ "foo": [ "bar", 1, { "baz": "thud" } ] }'` - - return eval("(" + json + ")"); // Object -} - -dojo._escapeString = function(/*String*/str){ - //summary: - // Adds escape sequences for non-visual characters, double quote and - // backslash and surrounds with double quotes to form a valid string - // literal. - return ('"' + str.replace(/(["\\])/g, '\\$1') + '"'). - replace(/[\f]/g, "\\f").replace(/[\b]/g, "\\b").replace(/[\n]/g, "\\n"). - replace(/[\t]/g, "\\t").replace(/[\r]/g, "\\r"); // string -} - -dojo.toJsonIndentStr = "\t"; -dojo.toJson = function(/*Object*/ it, /*Boolean?*/ prettyPrint, /*String?*/ _indentStr){ - // summary: - // Returns a [JSON](http://json.org) serialization of an object. - // - // description: - // Returns a [JSON](http://json.org) serialization of an object. - // Note that this doesn't check for infinite recursion, so don't do that! - // - // it: - // an object to be serialized. Objects may define their own - // serialization via a special "__json__" or "json" function - // property. If a specialized serializer has been defined, it will - // be used as a fallback. - // - // prettyPrint: - // if true, we indent objects and arrays to make the output prettier. - // The variable dojo.toJsonIndentStr is used as the indent string - // -- to use something other than the default (tab), - // change that variable before calling dojo.toJson(). - // - // _indentStr: - // private variable for recursive calls when pretty printing, do not use. - - if(it === undefined){ - return "undefined"; - } - var objtype = typeof it; - if(objtype == "number" || objtype == "boolean"){ - return it + ""; - } - if(it === null){ - return "null"; - } - if(dojo.isString(it)){ - return dojo._escapeString(it); - } - if(it.nodeType && it.cloneNode){ // isNode - return ""; // FIXME: would something like outerHTML be better here? - } - // recurse - var recurse = arguments.callee; - // short-circuit for objects that support "json" serialization - // if they return "self" then just pass-through... - var newObj; - _indentStr = _indentStr || ""; - var nextIndent = prettyPrint ? _indentStr + dojo.toJsonIndentStr : ""; - if(typeof it.__json__ == "function"){ - newObj = it.__json__(); - if(it !== newObj){ - return recurse(newObj, prettyPrint, nextIndent); - } - } - if(typeof it.json == "function"){ - newObj = it.json(); - if(it !== newObj){ - return recurse(newObj, prettyPrint, nextIndent); - } - } - - var sep = prettyPrint ? " " : ""; - var newLine = prettyPrint ? "\n" : ""; - - // array - if(dojo.isArray(it)){ - var res = dojo.map(it, function(obj){ - var val = recurse(obj, prettyPrint, nextIndent); - if(typeof val != "string"){ - val = "undefined"; - } - return newLine + nextIndent + val; - }); - return "[" + res.join("," + sep) + newLine + _indentStr + "]"; - } - /* - // look in the registry - try { - window.o = it; - newObj = dojo.json.jsonRegistry.match(it); - return recurse(newObj, prettyPrint, nextIndent); - }catch(e){ - // console.debug(e); - } - // it's a function with no adapter, skip it - */ - if(objtype == "function"){ - return null; // null - } - // generic object code path - var output = []; - for(var key in it){ - var keyStr; - if(typeof key == "number"){ - keyStr = '"' + key + '"'; - }else if(typeof key == "string"){ - keyStr = dojo._escapeString(key); - }else{ - // skip non-string or number keys - continue; - } - val = recurse(it[key], prettyPrint, nextIndent); - if(typeof val != "string"){ - // skip non-serializable values - continue; - } - // FIXME: use += on Moz!! - // MOW NOTE: using += is a pain because you have to account for the dangling comma... - output.push(newLine + nextIndent + keyStr + ":" + sep + val); - } - return "{" + output.join("," + sep) + newLine + _indentStr + "}"; // String -} - -} - -if(!dojo._hasResource["dojo._base.array"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.array"] = true; - -dojo.provide("dojo._base.array"); - -(function(){ - var _getParts = function(arr, obj, cb){ - return [ - dojo.isString(arr) ? arr.split("") : arr, - obj || dojo.global, - // FIXME: cache the anonymous functions we create here? - dojo.isString(cb) ? new Function("item", "index", "array", cb) : cb - ]; - }; - - dojo.mixin(dojo, { - indexOf: function( /*Array*/ array, - /*Object*/ value, - /*Integer?*/ fromIndex, - /*Boolean?*/ findLast){ - // summary: - // locates the first index of the provided value in the - // passed array. If the value is not found, -1 is returned. - // description: - // For details on this method, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:indexOf> - - var step = 1, end = array.length || 0, i = 0; - if(findLast){ - i = end - 1; - step = end = -1; - } - if(fromIndex != undefined){ i = fromIndex; } - if((findLast && i > end) || i < end){ - for(; i != end; i += step){ - if(array[i] == value){ return i; } - } - } - return -1; // Number - }, - - lastIndexOf: function(/*Array*/array, /*Object*/value, /*Integer?*/fromIndex){ - // summary: - // locates the last index of the provided value in the passed array. - // If the value is not found, -1 is returned. - // description: - // For details on this method, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:lastIndexOf> - return dojo.indexOf(array, value, fromIndex, true); // Number - }, - - forEach: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ - // summary: - // for every item in arr, callback is invoked. Return values are ignored. - // arr: the array to iterate on. If a string, operates on individual characters. - // callback: a function is invoked with three arguments: item, index, and array - // thisObject: may be used to scope the call to callback - // description: - // This function corresponds to the JavaScript 1.6 Array.forEach() method. - // In environments that support JavaScript 1.6, this function is a passthrough to the built-in method. - // For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:forEach> - - // match the behavior of the built-in forEach WRT empty arrs - if(!arr || !arr.length){ return; } - - // FIXME: there are several ways of handilng thisObject. Is - // dojo.global always the default context? - var _p = _getParts(arr, thisObject, callback); arr = _p[0]; - for(var i=0,l=_p[0].length; i<l; i++){ - _p[2].call(_p[1], arr[i], i, arr); - } - }, - - _everyOrSome: function(/*Boolean*/every, /*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ - var _p = _getParts(arr, thisObject, callback); arr = _p[0]; - for(var i = 0, l = arr.length; i < l; i++){ - var result = !!_p[2].call(_p[1], arr[i], i, arr); - if(every ^ result){ - return result; // Boolean - } - } - return every; // Boolean - }, - - every: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ - // summary: - // Determines whether or not every item in arr satisfies the - // condition implemented by callback. - // arr: the array to iterate on. If a string, operates on individual characters. - // callback: a function is invoked with three arguments: item, index, and array and returns true - // if the condition is met. - // thisObject: may be used to scope the call to callback - // description: - // This function corresponds to the JavaScript 1.6 Array.every() method. - // In environments that support JavaScript 1.6, this function is a passthrough to the built-in method. - // For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:every> - // example: - // | dojo.every([1, 2, 3, 4], function(item){ return item>1; }); - // returns false - // example: - // | dojo.every([1, 2, 3, 4], function(item){ return item>0; }); - // returns true - return this._everyOrSome(true, arr, callback, thisObject); // Boolean - }, - - some: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ - // summary: - // Determines whether or not any item in arr satisfies the - // condition implemented by callback. - // arr: the array to iterate on. If a string, operates on individual characters. - // callback: a function is invoked with three arguments: item, index, and array and returns true - // if the condition is met. - // thisObject: may be used to scope the call to callback - // description: - // This function corresponds to the JavaScript 1.6 Array.some() method. - // In environments that support JavaScript 1.6, this function is a passthrough to the built-in method. - // For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:some> - // example: - // | dojo.some([1, 2, 3, 4], function(item){ return item>1; }); - // returns true - // example: - // | dojo.some([1, 2, 3, 4], function(item){ return item<1; }); - // returns false - return this._everyOrSome(false, arr, callback, thisObject); // Boolean - }, - - map: function(/*Array|String*/arr, /*Function|String*/callback, /*Function?*/thisObject){ - // summary: - // applies callback to each element of arr and returns - // an Array with the results - // arr: the array to iterate on. If a string, operates on individual characters. - // callback: a function is invoked with three arguments: item, index, and array and returns a value - // thisObject: may be used to scope the call to callback - // description: - // This function corresponds to the JavaScript 1.6 Array.map() method. - // In environments that support JavaScript 1.6, this function is a passthrough to the built-in method. - // For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:map> - // example: - // | dojo.map([1, 2, 3, 4], function(item){ return item+1 }); - // returns [2, 3, 4, 5] - var _p = _getParts(arr, thisObject, callback); arr = _p[0]; - var outArr = (arguments[3] ? (new arguments[3]()) : []); - for(var i=0;i<arr.length;++i){ - outArr.push(_p[2].call(_p[1], arr[i], i, arr)); - } - return outArr; // Array - }, - - filter: function(/*Array*/arr, /*Function|String*/callback, /*Object?*/thisObject){ - // summary: - // Returns a new Array with those items from arr that match the - // condition implemented by callback. - // arr: the array to iterate on. If a string, operates on individual characters. - // callback: a function is invoked with three arguments: item, index, and array and returns true - // if the condition is met. - // thisObject: may be used to scope the call to callback - // description: - // This function corresponds to the JavaScript 1.6 Array.filter() method. - // In environments that support JavaScript 1.6, this function is a passthrough to the built-in method. - // For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:filter> - // example: - // | dojo.filter([1, 2, 3, 4], function(item){ return item>1; }); - // returns [2, 3, 4] - - var _p = _getParts(arr, thisObject, callback); arr = _p[0]; - var outArr = []; - for(var i = 0; i < arr.length; i++){ - if(_p[2].call(_p[1], arr[i], i, arr)){ - outArr.push(arr[i]); - } - } - return outArr; // Array - } - }); -})(); - -} - -if(!dojo._hasResource["dojo._base.Color"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.Color"] = true; -dojo.provide("dojo._base.Color"); - - - -dojo.Color = function(/*Array|String|Object*/ color){ - // summary: - // takes a named string, hex string, array of rgb or rgba values, - // an object with r, g, b, and a properties, or another dojo.Color object - if(color){ this.setColor(color); } -}; - -// FIXME: there's got to be a more space-efficient way to encode or discover these!! Use hex? -dojo.Color.named = { - black: [0,0,0], - silver: [192,192,192], - gray: [128,128,128], - white: [255,255,255], - maroon: [128,0,0], - red: [255,0,0], - purple: [128,0,128], - fuchsia: [255,0,255], - green: [0,128,0], - lime: [0,255,0], - olive: [128,128,0], - yellow: [255,255,0], - navy: [0,0,128], - blue: [0,0,255], - teal: [0,128,128], - aqua: [0,255,255] -}; - - -dojo.extend(dojo.Color, { - r: 255, g: 255, b: 255, a: 1, - _set: function(r, g, b, a){ - var t = this; t.r = r; t.g = g; t.b = b; t.a = a; - }, - setColor: function(/*Array|String|Object*/ color){ - // summary: - // takes a named string, hex string, array of rgb or rgba values, - // an object with r, g, b, and a properties, or another dojo.Color object - var d = dojo; - if(d.isString(color)){ - d.colorFromString(color, this); - }else if(d.isArray(color)){ - d.colorFromArray(color, this); - }else{ - this._set(color.r, color.g, color.b, color.a); - if(!(color instanceof d.Color)){ this.sanitize(); } - } - return this; // dojo.Color - }, - sanitize: function(){ - // summary: - // makes sure that the object has correct attributes - // description: - // the default implementation does nothing, include dojo.colors to - // augment it to real checks - return this; // dojo.Color - }, - toRgb: function(){ - // summary: returns 3 component array of rgb values - var t = this; - return [t.r, t.g, t.b]; // Array - }, - toRgba: function(){ - // summary: returns a 4 component array of rgba values - var t = this; - return [t.r, t.g, t.b, t.a]; // Array - }, - toHex: function(){ - // summary: returns a css color string in hexadecimal representation - var arr = dojo.map(["r", "g", "b"], function(x){ - var s = this[x].toString(16); - return s.length < 2 ? "0" + s : s; - }, this); - return "#" + arr.join(""); // String - }, - toCss: function(/*Boolean?*/ includeAlpha){ - // summary: returns a css color string in rgb(a) representation - var t = this, rgb = t.r + ", " + t.g + ", " + t.b; - return (includeAlpha ? "rgba(" + rgb + ", " + t.a : "rgb(" + rgb) + ")"; // String - }, - toString: function(){ - // summary: returns a visual representation of the color - return this.toCss(true); // String - } -}); - -dojo.blendColors = function( - /*dojo.Color*/ start, - /*dojo.Color*/ end, - /*Number*/ weight, - /*dojo.Color?*/ obj -){ - // summary: - // blend colors end and start with weight from 0 to 1, 0.5 being a 50/50 blend, - // can reuse a previously allocated dojo.Color object for the result - var d = dojo, t = obj || new dojo.Color(); - d.forEach(["r", "g", "b", "a"], function(x){ - t[x] = start[x] + (end[x] - start[x]) * weight; - if(x != "a"){ t[x] = Math.round(t[x]); } - }); - return t.sanitize(); // dojo.Color -}; - -dojo.colorFromRgb = function(/*String*/ color, /*dojo.Color?*/ obj){ - // summary: get rgb(a) array from css-style color declarations - var m = color.toLowerCase().match(/^rgba?\(([\s\.,0-9]+)\)/); - return m && dojo.colorFromArray(m[1].split(/\s*,\s*/), obj); // dojo.Color -}; - -dojo.colorFromHex = function(/*String*/ color, /*dojo.Color?*/ obj){ - // summary: converts a hex string with a '#' prefix to a color object. - // Supports 12-bit #rgb shorthand. - var d = dojo, t = obj || new d.Color(), - bits = (color.length == 4) ? 4 : 8, - mask = (1 << bits) - 1; - color = Number("0x" + color.substr(1)); - if(isNaN(color)){ - return null; // dojo.Color - } - d.forEach(["b", "g", "r"], function(x){ - var c = color & mask; - color >>= bits; - t[x] = bits == 4 ? 17 * c : c; - }); - t.a = 1; - return t; // dojo.Color -}; - -dojo.colorFromArray = function(/*Array*/ a, /*dojo.Color?*/ obj){ - // summary: builds a color from 1, 2, 3, or 4 element array - var t = obj || new dojo.Color(); - t._set(Number(a[0]), Number(a[1]), Number(a[2]), Number(a[3])); - if(isNaN(t.a)){ t.a = 1; } - return t.sanitize(); // dojo.Color -}; - -dojo.colorFromString = function(/*String*/ str, /*dojo.Color?*/ obj){ - // summary: - // parses str for a color value. - // description: - // Acceptable input values for str may include arrays of any form - // accepted by dojo.colorFromArray, hex strings such as "#aaaaaa", or - // rgb or rgba strings such as "rgb(133, 200, 16)" or "rgba(10, 10, - // 10, 50)" - // returns: - // a dojo.Color object. If obj is passed, it will be the return value. - var a = dojo.Color.named[str]; - return a && dojo.colorFromArray(a, obj) || dojo.colorFromRgb(str, obj) || dojo.colorFromHex(str, obj); -}; - -} - -if(!dojo._hasResource["dojo._base"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base"] = true; -dojo.provide("dojo._base"); - - - - - - - - - -} - -if(!dojo._hasResource["dojo._base.window"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.window"] = true; -dojo.provide("dojo._base.window"); - -dojo._gearsObject = function(){ - // summary: - // factory method to get a Google Gears plugin instance to - // expose in the browser runtime environment, if present - var factory; - var results; - - var gearsObj = dojo.getObject("google.gears"); - if(gearsObj){ return gearsObj; } // already defined elsewhere - - if(typeof GearsFactory != "undefined"){ // Firefox - factory = new GearsFactory(); - }else{ - if(dojo.isIE){ - // IE - try{ - factory = new ActiveXObject("Gears.Factory"); - }catch(e){ - // ok to squelch; there's no gears factory. move on. - } - }else if(navigator.mimeTypes["application/x-googlegears"]){ - // Safari? - factory = document.createElement("object"); - factory.setAttribute("type", "application/x-googlegears"); - factory.setAttribute("width", 0); - factory.setAttribute("height", 0); - factory.style.display = "none"; - document.documentElement.appendChild(factory); - } - } - - // still nothing? - if(!factory){ return null; } - - // define the global objects now; don't overwrite them though if they - // were somehow set internally by the Gears plugin, which is on their - // dev roadmap for the future - dojo.setObject("google.gears.factory", factory); - return dojo.getObject("google.gears"); -}; - -/*===== -dojo.isGears = { - // summary: True if client is using Google Gears -}; -=====*/ -// see if we have Google Gears installed, and if -// so, make it available in the runtime environment -// and in the Google standard 'google.gears' global object -dojo.isGears = (!!dojo._gearsObject())||0; - -/*===== -dojo.doc = { - // summary: - // Alias for the current document. 'dojo.doc' can be modified - // for temporary context shifting. Also see dojo.withDoc(). - // description: - // Refer to dojo.doc rather - // than referring to 'window.document' to ensure your code runs - // correctly in managed contexts. - // example: - // | n.appendChild(dojo.doc.createElement('div')); -} -=====*/ -dojo.doc = window["document"] || null; - -dojo.body = function(){ - // summary: - // Return the body element of the document - // return the body object associated with dojo.doc - // example: - // | dojo.body().appendChild(dojo.doc.createElement('div')); - - // Note: document.body is not defined for a strict xhtml document - // Would like to memoize this, but dojo.doc can change vi dojo.withDoc(). - return dojo.doc.body || dojo.doc.getElementsByTagName("body")[0]; // Node -} - -dojo.setContext = function(/*Object*/globalObject, /*DocumentElement*/globalDocument){ - // summary: - // changes the behavior of many core Dojo functions that deal with - // namespace and DOM lookup, changing them to work in a new global - // context (e.g., an iframe). The varibles dojo.global and dojo.doc - // are modified as a result of calling this function and the result of - // `dojo.body()` likewise differs. - dojo.global = globalObject; - dojo.doc = globalDocument; -}; - -dojo._fireCallback = function(callback, context, cbArguments){ - if(context && dojo.isString(callback)){ - callback = context[callback]; - } - return callback.apply(context, cbArguments || [ ]); -} - -dojo.withGlobal = function( /*Object*/globalObject, - /*Function*/callback, - /*Object?*/thisObject, - /*Array?*/cbArguments){ - // summary: - // Call callback with globalObject as dojo.global and - // globalObject.document as dojo.doc. If provided, globalObject - // will be executed in the context of object thisObject - // description: - // When callback() returns or throws an error, the dojo.global - // and dojo.doc will be restored to its previous state. - var rval; - var oldGlob = dojo.global; - var oldDoc = dojo.doc; - try{ - dojo.setContext(globalObject, globalObject.document); - rval = dojo._fireCallback(callback, thisObject, cbArguments); - }finally{ - dojo.setContext(oldGlob, oldDoc); - } - return rval; -} - -dojo.withDoc = function( /*Object*/documentObject, - /*Function*/callback, - /*Object?*/thisObject, - /*Array?*/cbArguments){ - // summary: - // Call callback with documentObject as dojo.doc. If provided, - // callback will be executed in the context of object thisObject - // description: - // When callback() returns or throws an error, the dojo.doc will - // be restored to its previous state. - var rval; - var oldDoc = dojo.doc; - try{ - dojo.doc = documentObject; - rval = dojo._fireCallback(callback, thisObject, cbArguments); - }finally{ - dojo.doc = oldDoc; - } - return rval; -}; - -} - -if(!dojo._hasResource["dojo._base.event"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.event"] = true; -dojo.provide("dojo._base.event"); - - -// this file courtesy of the TurboAjax Group, licensed under a Dojo CLA - -(function(){ - // DOM event listener machinery - var del = (dojo._event_listener = { - add: function(/*DOMNode*/node, /*String*/name, /*Function*/fp){ - if(!node){return;} - name = del._normalizeEventName(name); - fp = del._fixCallback(name, fp); - var oname = name; - if(!dojo.isIE && (name == "mouseenter" || name == "mouseleave")){ - var ofp = fp; - //oname = name; - name = (name == "mouseenter") ? "mouseover" : "mouseout"; - fp = function(e){ - // thanks ben! - if(!dojo.isDescendant(e.relatedTarget, node)){ - // e.type = oname; // FIXME: doesn't take? SJM: event.type is generally immutable. - return ofp.call(this, e); - } - } - } - node.addEventListener(name, fp, false); - return fp; /*Handle*/ - }, - remove: function(/*DOMNode*/node, /*String*/event, /*Handle*/handle){ - // summary: - // clobbers the listener from the node - // node: - // DOM node to attach the event to - // event: - // the name of the handler to remove the function from - // handle: - // the handle returned from add - if (node){ - node.removeEventListener(del._normalizeEventName(event), handle, false); - } - }, - _normalizeEventName: function(/*String*/name){ - // Generally, name should be lower case, unless it is special - // somehow (e.g. a Mozilla DOM event). - // Remove 'on'. - return name.slice(0,2) =="on" ? name.slice(2) : name; - }, - _fixCallback: function(/*String*/name, fp){ - // By default, we only invoke _fixEvent for 'keypress' - // If code is added to _fixEvent for other events, we have - // to revisit this optimization. - // This also applies to _fixEvent overrides for Safari and Opera - // below. - return name != "keypress" ? fp : function(e){ return fp.call(this, del._fixEvent(e, this)); }; - }, - _fixEvent: function(evt, sender){ - // _fixCallback only attaches us to keypress. - // Switch on evt.type anyway because we might - // be called directly from dojo.fixEvent. - switch(evt.type){ - case "keypress": - del._setKeyChar(evt); - break; - } - return evt; - }, - _setKeyChar: function(evt){ - evt.keyChar = evt.charCode ? String.fromCharCode(evt.charCode) : ''; - } - }); - - // DOM events - - dojo.fixEvent = function(/*Event*/evt, /*DOMNode*/sender){ - // summary: - // normalizes properties on the event object including event - // bubbling methods, keystroke normalization, and x/y positions - // evt: Event - // native event object - // sender: DOMNode - // node to treat as "currentTarget" - return del._fixEvent(evt, sender); - } - - dojo.stopEvent = function(/*Event*/evt){ - // summary: - // prevents propagation and clobbers the default action of the - // passed event - // evt: Event - // The event object. If omitted, window.event is used on IE. - evt.preventDefault(); - evt.stopPropagation(); - // NOTE: below, this method is overridden for IE - } - - // the default listener to use on dontFix nodes, overriden for IE - var node_listener = dojo._listener; - - // Unify connect and event listeners - dojo._connect = function(obj, event, context, method, dontFix){ - // FIXME: need a more strict test - var isNode = obj && (obj.nodeType||obj.attachEvent||obj.addEventListener); - // choose one of three listener options: raw (connect.js), DOM event on a Node, custom event on a Node - // we need the third option to provide leak prevention on broken browsers (IE) - var lid = !isNode ? 0 : (!dontFix ? 1 : 2), l = [dojo._listener, del, node_listener][lid]; - // create a listener - var h = l.add(obj, event, dojo.hitch(context, method)); - // formerly, the disconnect package contained "l" directly, but if client code - // leaks the disconnect package (by connecting it to a node), referencing "l" - // compounds the problem. - // instead we return a listener id, which requires custom _disconnect below. - // return disconnect package - return [ obj, event, h, lid ]; - } - - dojo._disconnect = function(obj, event, handle, listener){ - ([dojo._listener, del, node_listener][listener]).remove(obj, event, handle); - } - - // Constants - - // Public: client code should test - // keyCode against these named constants, as the - // actual codes can vary by browser. - dojo.keys = { - // summary: definitions for common key values - BACKSPACE: 8, - TAB: 9, - CLEAR: 12, - ENTER: 13, - SHIFT: 16, - CTRL: 17, - ALT: 18, - PAUSE: 19, - CAPS_LOCK: 20, - ESCAPE: 27, - SPACE: 32, - PAGE_UP: 33, - PAGE_DOWN: 34, - END: 35, - HOME: 36, - LEFT_ARROW: 37, - UP_ARROW: 38, - RIGHT_ARROW: 39, - DOWN_ARROW: 40, - INSERT: 45, - DELETE: 46, - HELP: 47, - LEFT_WINDOW: 91, - RIGHT_WINDOW: 92, - SELECT: 93, - NUMPAD_0: 96, - NUMPAD_1: 97, - NUMPAD_2: 98, - NUMPAD_3: 99, - NUMPAD_4: 100, - NUMPAD_5: 101, - NUMPAD_6: 102, - NUMPAD_7: 103, - NUMPAD_8: 104, - NUMPAD_9: 105, - NUMPAD_MULTIPLY: 106, - NUMPAD_PLUS: 107, - NUMPAD_ENTER: 108, - NUMPAD_MINUS: 109, - NUMPAD_PERIOD: 110, - NUMPAD_DIVIDE: 111, - F1: 112, - F2: 113, - F3: 114, - F4: 115, - F5: 116, - F6: 117, - F7: 118, - F8: 119, - F9: 120, - F10: 121, - F11: 122, - F12: 123, - F13: 124, - F14: 125, - F15: 126, - NUM_LOCK: 144, - SCROLL_LOCK: 145 - }; - - // IE event normalization - if(dojo.isIE){ - var _trySetKeyCode = function(e, code){ - try{ - // squelch errors when keyCode is read-only - // (e.g. if keyCode is ctrl or shift) - return (e.keyCode = code); - }catch(e){ - return 0; - } - } - - // by default, use the standard listener - var iel = dojo._listener; - // dispatcher tracking property - if(!dojo.config._allow_leaks){ - // custom listener that handles leak protection for DOM events - node_listener = iel = dojo._ie_listener = { - // support handler indirection: event handler functions are - // referenced here. Event dispatchers hold only indices. - handlers: [], - // add a listener to an object - add: function(/*Object*/ source, /*String*/ method, /*Function*/ listener){ - source = source || dojo.global; - var f = source[method]; - if(!f||!f._listeners){ - var d = dojo._getIeDispatcher(); - // original target function is special - d.target = f && (ieh.push(f) - 1); - // dispatcher holds a list of indices into handlers table - d._listeners = []; - // redirect source to dispatcher - f = source[method] = d; - } - return f._listeners.push(ieh.push(listener) - 1) ; /*Handle*/ - }, - // remove a listener from an object - remove: function(/*Object*/ source, /*String*/ method, /*Handle*/ handle){ - var f = (source||dojo.global)[method], l = f && f._listeners; - if(f && l && handle--){ - delete ieh[l[handle]]; - delete l[handle]; - } - } - }; - // alias used above - var ieh = iel.handlers; - } - - dojo.mixin(del, { - add: function(/*DOMNode*/node, /*String*/event, /*Function*/fp){ - if(!node){return;} // undefined - event = del._normalizeEventName(event); - if(event=="onkeypress"){ - // we need to listen to onkeydown to synthesize - // keypress events that otherwise won't fire - // on IE - var kd = node.onkeydown; - if(!kd || !kd._listeners || !kd._stealthKeydownHandle){ - var h = del.add(node, "onkeydown", del._stealthKeyDown); - kd = node.onkeydown; - kd._stealthKeydownHandle = h; - kd._stealthKeydownRefs = 1; - }else{ - kd._stealthKeydownRefs++; - } - } - return iel.add(node, event, del._fixCallback(fp)); - }, - remove: function(/*DOMNode*/node, /*String*/event, /*Handle*/handle){ - event = del._normalizeEventName(event); - iel.remove(node, event, handle); - if(event=="onkeypress"){ - var kd = node.onkeydown; - if(--kd._stealthKeydownRefs <= 0){ - iel.remove(node, "onkeydown", kd._stealthKeydownHandle); - delete kd._stealthKeydownHandle; - } - } - }, - _normalizeEventName: function(/*String*/eventName){ - // Generally, eventName should be lower case, unless it is - // special somehow (e.g. a Mozilla event) - // ensure 'on' - return eventName.slice(0,2) != "on" ? "on" + eventName : eventName; - }, - _nop: function(){}, - _fixEvent: function(/*Event*/evt, /*DOMNode*/sender){ - // summary: - // normalizes properties on the event object including event - // bubbling methods, keystroke normalization, and x/y positions - // evt: native event object - // sender: node to treat as "currentTarget" - if(!evt){ - var w = sender && (sender.ownerDocument || sender.document || sender).parentWindow || window; - evt = w.event; - } - if(!evt){return(evt);} - evt.target = evt.srcElement; - evt.currentTarget = (sender || evt.srcElement); - evt.layerX = evt.offsetX; - evt.layerY = evt.offsetY; - // FIXME: scroll position query is duped from dojo.html to - // avoid dependency on that entire module. Now that HTML is in - // Base, we should convert back to something similar there. - var se = evt.srcElement, doc = (se && se.ownerDocument) || document; - // DO NOT replace the following to use dojo.body(), in IE, document.documentElement should be used - // here rather than document.body - var docBody = ((dojo.isIE < 6) || (doc["compatMode"] == "BackCompat")) ? doc.body : doc.documentElement; - var offset = dojo._getIeDocumentElementOffset(); - evt.pageX = evt.clientX + dojo._fixIeBiDiScrollLeft(docBody.scrollLeft || 0) - offset.x; - evt.pageY = evt.clientY + (docBody.scrollTop || 0) - offset.y; - if(evt.type == "mouseover"){ - evt.relatedTarget = evt.fromElement; - } - if(evt.type == "mouseout"){ - evt.relatedTarget = evt.toElement; - } - evt.stopPropagation = del._stopPropagation; - evt.preventDefault = del._preventDefault; - return del._fixKeys(evt); - }, - _fixKeys: function(evt){ - switch(evt.type){ - case "keypress": - var c = ("charCode" in evt ? evt.charCode : evt.keyCode); - if (c==10){ - // CTRL-ENTER is CTRL-ASCII(10) on IE, but CTRL-ENTER on Mozilla - c=0; - evt.keyCode = 13; - }else if(c==13||c==27){ - c=0; // Mozilla considers ENTER and ESC non-printable - }else if(c==3){ - c=99; // Mozilla maps CTRL-BREAK to CTRL-c - } - // Mozilla sets keyCode to 0 when there is a charCode - // but that stops the event on IE. - evt.charCode = c; - del._setKeyChar(evt); - break; - } - return evt; - }, - // some ctrl-key combinations (mostly w/punctuation) do not emit a char code in IE - // we map those virtual key codes to ascii here - // not valid for all (non-US) keyboards, so maybe we shouldn't bother - _punctMap: { - 106:42, - 111:47, - 186:59, - 187:43, - 188:44, - 189:45, - 190:46, - 191:47, - 192:96, - 219:91, - 220:92, - 221:93, - 222:39 - }, - _stealthKeyDown: function(evt){ - // IE doesn't fire keypress for most non-printable characters. - // other browsers do, we simulate it here. - var kp = evt.currentTarget.onkeypress; - // only works if kp exists and is a dispatcher - if(!kp || !kp._listeners){ return; } - // munge key/charCode - var k=evt.keyCode; - // These are Windows Virtual Key Codes - // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/WinUI/WindowsUserInterface/UserInput/VirtualKeyCodes.asp - var unprintable = (k!=13)&&(k!=32)&&(k!=27)&&(k<48||k>90)&&(k<96||k>111)&&(k<186||k>192)&&(k<219||k>222); - // synthesize keypress for most unprintables and CTRL-keys - if(unprintable||evt.ctrlKey){ - var c = unprintable ? 0 : k; - if(evt.ctrlKey){ - if(k==3 || k==13){ - return; // IE will post CTRL-BREAK, CTRL-ENTER as keypress natively - }else if(c>95 && c<106){ - c -= 48; // map CTRL-[numpad 0-9] to ASCII - }else if((!evt.shiftKey)&&(c>=65&&c<=90)){ - c += 32; // map CTRL-[A-Z] to lowercase - }else{ - c = del._punctMap[c] || c; // map other problematic CTRL combinations to ASCII - } - } - // simulate a keypress event - var faux = del._synthesizeEvent(evt, {type: 'keypress', faux: true, charCode: c}); - kp.call(evt.currentTarget, faux); - evt.cancelBubble = faux.cancelBubble; - evt.returnValue = faux.returnValue; - _trySetKeyCode(evt, faux.keyCode); - } - }, - // Called in Event scope - _stopPropagation: function(){ - this.cancelBubble = true; - }, - _preventDefault: function(){ - // Setting keyCode to 0 is the only way to prevent certain keypresses (namely - // ctrl-combinations that correspond to menu accelerator keys). - // Otoh, it prevents upstream listeners from getting this information - // Try to split the difference here by clobbering keyCode only for ctrl - // combinations. If you still need to access the key upstream, bubbledKeyCode is - // provided as a workaround. - this.bubbledKeyCode = this.keyCode; - if(this.ctrlKey){_trySetKeyCode(this, 0);} - this.returnValue = false; - } - }); - - // override stopEvent for IE - dojo.stopEvent = function(evt){ - evt = evt || window.event; - del._stopPropagation.call(evt); - del._preventDefault.call(evt); - } - } - - del._synthesizeEvent = function(evt, props){ - var faux = dojo.mixin({}, evt, props); - del._setKeyChar(faux); - // FIXME: would prefer to use dojo.hitch: dojo.hitch(evt, evt.preventDefault); - // but it throws an error when preventDefault is invoked on Safari - // does Event.preventDefault not support "apply" on Safari? - faux.preventDefault = function(){ evt.preventDefault(); }; - faux.stopPropagation = function(){ evt.stopPropagation(); }; - return faux; - } - - // Opera event normalization - if(dojo.isOpera){ - dojo.mixin(del, { - _fixEvent: function(evt, sender){ - switch(evt.type){ - case "keypress": - var c = evt.which; - if(c==3){ - c=99; // Mozilla maps CTRL-BREAK to CTRL-c - } - // can't trap some keys at all, like INSERT and DELETE - // there is no differentiating info between DELETE and ".", or INSERT and "-" - c = ((c<41)&&(!evt.shiftKey) ? 0 : c); - if((evt.ctrlKey)&&(!evt.shiftKey)&&(c>=65)&&(c<=90)){ - // lowercase CTRL-[A-Z] keys - c += 32; - } - return del._synthesizeEvent(evt, { charCode: c }); - } - return evt; - } - }); - } - - // Safari event normalization - if(dojo.isSafari){ - dojo.mixin(del, { - _fixEvent: function(evt, sender){ - switch(evt.type){ - case "keypress": - var c = evt.charCode, s = evt.shiftKey, k = evt.keyCode; - // FIXME: This is a hack, suggest we rethink keyboard strategy. - // Arrow and page keys have 0 "keyCode" in keypress events.on Safari for Windows - k = k || identifierMap[evt.keyIdentifier] || 0; - if(evt.keyIdentifier=="Enter"){ - c = 0; // differentiate Enter from CTRL-m (both code 13) - }else if((evt.ctrlKey)&&(c>0)&&(c<27)){ - c += 96; // map CTRL-[A-Z] codes to ASCII - } else if (c==dojo.keys.SHIFT_TAB) { - c = dojo.keys.TAB; // morph SHIFT_TAB into TAB + shiftKey: true - s = true; - } else { - c = (c>=32 && c<63232 ? c : 0); // avoid generating keyChar for non-printables - } - return del._synthesizeEvent(evt, {charCode: c, shiftKey: s, keyCode: k}); - } - return evt; - } - }); - - dojo.mixin(dojo.keys, { - SHIFT_TAB: 25, - UP_ARROW: 63232, - DOWN_ARROW: 63233, - LEFT_ARROW: 63234, - RIGHT_ARROW: 63235, - F1: 63236, - F2: 63237, - F3: 63238, - F4: 63239, - F5: 63240, - F6: 63241, - F7: 63242, - F8: 63243, - F9: 63244, - F10: 63245, - F11: 63246, - F12: 63247, - PAUSE: 63250, - DELETE: 63272, - HOME: 63273, - END: 63275, - PAGE_UP: 63276, - PAGE_DOWN: 63277, - INSERT: 63302, - PRINT_SCREEN: 63248, - SCROLL_LOCK: 63249, - NUM_LOCK: 63289 - }); - var dk = dojo.keys, identifierMap = { "Up": dk.UP_ARROW, "Down": dk.DOWN_ARROW, "Left": dk.LEFT_ARROW, "Right": dk.RIGHT_ARROW, "PageUp": dk.PAGE_UP, "PageDown": dk.PAGE_DOWN }; - } -})(); - -if(dojo.isIE){ - // keep this out of the closure - // closing over 'iel' or 'ieh' b0rks leak prevention - // ls[i] is an index into the master handler array - dojo._ieDispatcher = function(args, sender){ - var ap=Array.prototype, h=dojo._ie_listener.handlers, c=args.callee, ls=c._listeners, t=h[c.target]; - // return value comes from original target function - var r = t && t.apply(sender, args); - // invoke listeners after target function - for(var i in ls){ - if(!(i in ap)){ - h[ls[i]].apply(sender, args); - } - } - return r; - } - dojo._getIeDispatcher = function(){ - // ensure the returned function closes over nothing - return new Function(dojo._scopeName + "._ieDispatcher(arguments, this)"); // function - } - // keep this out of the closure to reduce RAM allocation - dojo._event_listener._fixCallback = function(fp){ - var f = dojo._event_listener._fixEvent; - return function(e){ return fp.call(this, f(e, this)); }; - } -} - -} - -if(!dojo._hasResource["dojo._base.html"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.html"] = true; - -dojo.provide("dojo._base.html"); - -// FIXME: need to add unit tests for all the semi-public methods - -try{ - document.execCommand("BackgroundImageCache", false, true); -}catch(e){ - // sane browsers don't have cache "issues" -} - -// ============================= -// DOM Functions -// ============================= - -/*===== -dojo.byId = function(id, doc){ - // summary: - // Returns DOM node with matching `id` attribute or `null` - // if not found, similar to "$" function in another library. - // If `id` is a DomNode, this function is a no-op. - // - // id: String|DOMNode - // A string to match an HTML id attribute or a reference to a DOM Node - // - // doc: Document? - // Document to work in. Defaults to the current value of - // dojo.doc. Can be used to retrieve - // node references from other documents. -=====*/ -if(dojo.isIE || dojo.isOpera){ - dojo.byId = function(id, doc){ - if(dojo.isString(id)){ - var _d = doc || dojo.doc; - var te = _d.getElementById(id); - // attributes.id.value is better than just id in case the - // user has a name=id inside a form - if(te && te.attributes.id.value == id){ - return te; - }else{ - var eles = _d.all[id]; - if(!eles || !eles.length){ return eles; } - // if more than 1, choose first with the correct id - var i=0; - while((te=eles[i++])){ - if(te.attributes.id.value == id){ return te; } - } - } - }else{ - return id; // DomNode - } - } -}else{ - dojo.byId = function(id, doc){ - return dojo.isString(id) ? (doc || dojo.doc).getElementById(id) : id; // DomNode - } -} -/*===== -} -=====*/ - -(function(){ - /* - dojo.createElement = function(obj, parent, position){ - // TODO: need to finish this! - } - */ - - var d = dojo; - - var _destroyContainer = null; - dojo.addOnUnload(function(){ - _destroyContainer=null; //prevent IE leak - }); - dojo._destroyElement = function(/*String||DomNode*/node){ - // summary: - // removes node from its parent, clobbers it and all of its - // children. - // node: - // the element to be destroyed, either as an ID or a reference - - node = d.byId(node); - try{ - if(!_destroyContainer){ - _destroyContainer = document.createElement("div"); - } - _destroyContainer.appendChild(node.parentNode ? node.parentNode.removeChild(node) : node); - // NOTE: see http://trac.dojotoolkit.org/ticket/2931. This may be a bug and not a feature - _destroyContainer.innerHTML = ""; - }catch(e){ - /* squelch */ - } - }; - - dojo.isDescendant = function(/*DomNode|String*/node, /*DomNode|String*/ancestor){ - // summary: - // Returns true if node is a descendant of ancestor - // node: id or node reference to test - // ancestor: id or node reference of potential parent to test against - try{ - node = d.byId(node); - ancestor = d.byId(ancestor); - while(node){ - if(node === ancestor){ - return true; // Boolean - } - node = node.parentNode; - } - }catch(e){ /* squelch, return false */ } - return false; // Boolean - }; - - dojo.setSelectable = function(/*DomNode|String*/node, /*Boolean*/selectable){ - // summary: enable or disable selection on a node - // node: - // id or reference to node - // selectable: - node = d.byId(node); - if(d.isMozilla){ - node.style.MozUserSelect = selectable ? "" : "none"; - }else if(d.isKhtml){ - node.style.KhtmlUserSelect = selectable ? "auto" : "none"; - }else if(d.isIE){ - node.unselectable = selectable ? "" : "on"; - d.query("*", node).forEach(function(descendant){ - descendant.unselectable = selectable ? "" : "on"; - }); - } - //FIXME: else? Opera? - }; - - var _insertBefore = function(/*Node*/node, /*Node*/ref){ - ref.parentNode.insertBefore(node, ref); - return true; // boolean - } - - var _insertAfter = function(/*Node*/node, /*Node*/ref){ - // summary: - // Try to insert node after ref - var pn = ref.parentNode; - if(ref == pn.lastChild){ - pn.appendChild(node); - }else{ - return _insertBefore(node, ref.nextSibling); // boolean - } - return true; // boolean - } - - dojo.place = function(/*String|DomNode*/node, /*String|DomNode*/refNode, /*String|Number*/position){ - // summary: - // Attempt to insert node into the DOM, choosing from various positioning options. - // Returns true if successful, false otherwise. - // node: - // id or node reference to place relative to refNode - // refNode: - // id or node reference to use as basis for placement - // position: - // string noting the position of node relative to refNode or a - // number indicating the location in the childNodes collection of - // refNode. Accepted string values are: - // - // * before - // * after - // * first - // * last - // - // "first" and "last" indicate positions as children of refNode. - - // FIXME: need to write tests for this!!!! - if(!node || !refNode || position === undefined){ - return false; // boolean - } - node = d.byId(node); - refNode = d.byId(refNode); - if(typeof position == "number"){ - var cn = refNode.childNodes; - if((position == 0 && cn.length == 0) || - cn.length == position){ - refNode.appendChild(node); return true; - } - if(position == 0){ - return _insertBefore(node, refNode.firstChild); - } - return _insertAfter(node, cn[position-1]); - } - switch(position.toLowerCase()){ - case "before": - return _insertBefore(node, refNode); // boolean - case "after": - return _insertAfter(node, refNode); // boolean - case "first": - if(refNode.firstChild){ - return _insertBefore(node, refNode.firstChild); // boolean - } - // else fallthrough... - default: // aka: last - refNode.appendChild(node); - return true; // boolean - } - } - - // Box functions will assume this model. - // On IE/Opera, BORDER_BOX will be set if the primary document is in quirks mode. - // Can be set to change behavior of box setters. - - // can be either: - // "border-box" - // "content-box" (default) - dojo.boxModel = "content-box"; - - // We punt per-node box mode testing completely. - // If anybody cares, we can provide an additional (optional) unit - // that overrides existing code to include per-node box sensitivity. - - // Opera documentation claims that Opera 9 uses border-box in BackCompat mode. - // but experiments (Opera 9.10.8679 on Windows Vista) indicate that it actually continues to use content-box. - // IIRC, earlier versions of Opera did in fact use border-box. - // Opera guys, this is really confusing. Opera being broken in quirks mode is not our fault. - - if(d.isIE /*|| dojo.isOpera*/){ - var _dcm = document.compatMode; - // client code may have to adjust if compatMode varies across iframes - d.boxModel = _dcm == "BackCompat" || _dcm == "QuirksMode" || d.isIE<6 ? "border-box" : "content-box"; // FIXME: remove IE < 6 support? - } - - // ============================= - // Style Functions - // ============================= - - // getComputedStyle drives most of the style code. - // Wherever possible, reuse the returned object. - // - // API functions below that need to access computed styles accept an - // optional computedStyle parameter. - // If this parameter is omitted, the functions will call getComputedStyle themselves. - // This way, calling code can access computedStyle once, and then pass the reference to - // multiple API functions. - -/*===== - dojo.getComputedStyle = function(node){ - // summary: - // Returns a "computed style" object. - // - // description: - // Gets a "computed style" object which can be used to gather - // information about the current state of the rendered node. - // - // Note that this may behave differently on different browsers. - // Values may have different formats and value encodings across - // browsers. - // - // Note also that this method is expensive. Wherever possible, - // reuse the returned object. - // - // Use the dojo.style() method for more consistent (pixelized) - // return values. - // - // node: DOMNode - // A reference to a DOM node. Does NOT support taking an - // ID string for speed reasons. - // example: - // | dojo.getComputedStyle(dojo.byId('foo')).borderWidth; - return; // CSS2Properties - } -=====*/ - - var gcs, dv = document.defaultView; - if(d.isSafari){ - gcs = function(/*DomNode*/node){ - var s = dv.getComputedStyle(node, null); - if(!s && node.style){ - node.style.display = ""; - s = dv.getComputedStyle(node, null); - } - return s || {}; - }; - }else if(d.isIE){ - gcs = function(node){ - return node.currentStyle; - }; - }else{ - gcs = function(node){ - return dv.getComputedStyle(node, null); - }; - } - dojo.getComputedStyle = gcs; - - if(!d.isIE){ - dojo._toPixelValue = function(element, value){ - // style values can be floats, client code may want - // to round for integer pixels. - return parseFloat(value) || 0; - } - }else{ - dojo._toPixelValue = function(element, avalue){ - if(!avalue){ return 0; } - // on IE7, medium is usually 4 pixels - if(avalue=="medium"){ return 4; } - // style values can be floats, client code may - // want to round this value for integer pixels. - if(avalue.slice && (avalue.slice(-2)=='px')){ return parseFloat(avalue); } - with(element){ - var sLeft = style.left; - var rsLeft = runtimeStyle.left; - runtimeStyle.left = currentStyle.left; - try{ - // 'avalue' may be incompatible with style.left, which can cause IE to throw - // this has been observed for border widths using "thin", "medium", "thick" constants - // those particular constants could be trapped by a lookup - // but perhaps there are more - style.left = avalue; - avalue = style.pixelLeft; - }catch(e){ - avalue = 0; - } - style.left = sLeft; - runtimeStyle.left = rsLeft; - } - return avalue; - } - } - var px = d._toPixelValue; - - // FIXME: there opacity quirks on FF that we haven't ported over. Hrm. - /*===== - dojo._getOpacity = function(node){ - // summary: - // Returns the current opacity of the passed node as a - // floating-point value between 0 and 1. - // node: DomNode - // a reference to a DOM node. Does NOT support taking an - // ID string for speed reasons. - // return: Number between 0 and 1 - } - =====*/ - - dojo._getOpacity = d.isIE ? function(node){ - try{ - return node.filters.alpha.opacity / 100; // Number - }catch(e){ - return 1; // Number - } - } : function(node){ - return gcs(node).opacity; - }; - - /*===== - dojo._setOpacity = function(node, opacity){ - // summary: - // set the opacity of the passed node portably. Returns the - // new opacity of the node. - // node: DOMNode - // a reference to a DOM node. Does NOT support taking an - // ID string for performance reasons. - // opacity: Number - // A Number between 0 and 1. 0 specifies transparent. - // return: Number between 0 and 1 - } - =====*/ - - dojo._setOpacity = d.isIE ? function(/*DomNode*/node, /*Number*/opacity){ - if(opacity == 1){ - // on IE7 Alpha(Filter opacity=100) makes text look fuzzy so remove it altogether (bug #2661) - var filterRE = /FILTER:[^;]*;?/i; - node.style.cssText = node.style.cssText.replace(filterRE, ""); - if(node.nodeName.toLowerCase() == "tr"){ - d.query("> td", node).forEach(function(i){ - i.style.cssText = i.style.cssText.replace(filterRE, ""); - }); - } - }else{ - var o = "Alpha(Opacity="+ opacity * 100 +")"; - node.style.filter = o; - } - if(node.nodeName.toLowerCase() == "tr"){ - d.query("> td", node).forEach(function(i){ - i.style.filter = o; - }); - } - return opacity; - } : function(node, opacity){ - return node.style.opacity = opacity; - }; - - var _pixelNamesCache = { - left: true, top: true - }; - var _pixelRegExp = /margin|padding|width|height|max|min|offset/; // |border - var _toStyleValue = function(node, type, value){ - type = type.toLowerCase(); - if(d.isIE && value == "auto"){ - if(type == "height"){ return node.offsetHeight; } - if(type == "width"){ return node.offsetWidth; } - } - if(!(type in _pixelNamesCache)){ - // if(dojo.isOpera && type == "cssText"){ - // FIXME: add workaround for #2855 here - // } - _pixelNamesCache[type] = _pixelRegExp.test(type); - } - return _pixelNamesCache[type] ? px(node, value) : value; - } - - var _floatStyle = d.isIE ? "styleFloat" : "cssFloat"; - var _floatAliases = { "cssFloat": _floatStyle, "styleFloat": _floatStyle, "float": _floatStyle }; - - // public API - - dojo.style = function( /*DomNode|String*/ node, - /*String?|Object?*/ style, - /*String?*/ value){ - // summary: - // Accesses styles on a node. If 2 arguments are - // passed, acts as a getter. If 3 arguments are passed, acts - // as a setter. - // node: - // id or reference to node to get/set style for - // style: - // the style property to set in DOM-accessor format - // ("borderWidth", not "border-width") or an object with key/value - // pairs suitable for setting each property. - // value: - // If passed, sets value on the node for style, handling - // cross-browser concerns. - // example: - // Passing only an ID or node returns the computed style object of - // the node: - // | dojo.style("thinger"); - // example: - // Passing a node and a style property returns the current - // normalized, computed value for that property: - // | dojo.style("thinger", "opacity"); // 1 by default - // - // example: - // Passing a node, a style property, and a value changes the - // current display of the node and returns the new computed value - // | dojo.style("thinger", "opacity", 0.5); // == 0.5 - // - // example: - // Passing a node, an object-style style property sets each of the values in turn and returns the computed style object of the node: - // | dojo.style("thinger", { - // | "opacity": 0.5, - // | "border": "3px solid black", - // | "height": 300 - // | }); - // - // example: - // When the CSS style property is hyphenated, the JavaScript property is camelCased. - // font-size becomes fontSize, and so on. - // | dojo.style("thinger",{ - // | fontSize:"14pt", - // | letterSpacing:"1.2em" - // | }); - // - // example: - // dojo.NodeList implements .style() using the same syntax, omitting the "node" parameter, calling - // dojo.style() on every element of the list. See: dojo.query and dojo.NodeList - // | dojo.query(".someClassName").style("visibility","hidden"); - // | // or - // | dojo.query("#baz > div").style({ - // | opacity:0.75, - // | fontSize:"13pt" - // | }); - - var n = d.byId(node), args = arguments.length, op = (style=="opacity"); - style = _floatAliases[style] || style; - if(args == 3){ - return op ? d._setOpacity(n, value) : n.style[style] = value; /*Number*/ - } - if(args == 2 && op){ - return d._getOpacity(n); - } - var s = gcs(n); - if(args == 2 && !d.isString(style)){ - for(var x in style){ - d.style(node, x, style[x]); - } - return s; - } - return (args == 1) ? s : _toStyleValue(n, style, s[style]); /* CSS2Properties||String||Number */ - } - - // ============================= - // Box Functions - // ============================= - - dojo._getPadExtents = function(/*DomNode*/n, /*Object*/computedStyle){ - // summary: - // Returns object with special values specifically useful for node - // fitting. - // - // * l/t = left/top padding (respectively) - // * w = the total of the left and right padding - // * h = the total of the top and bottom padding - // - // If 'node' has position, l/t forms the origin for child nodes. - // The w/h are used for calculating boxes. - // Normally application code will not need to invoke this - // directly, and will use the ...box... functions instead. - var - s = computedStyle||gcs(n), - l = px(n, s.paddingLeft), - t = px(n, s.paddingTop); - return { - l: l, - t: t, - w: l+px(n, s.paddingRight), - h: t+px(n, s.paddingBottom) - }; - } - - dojo._getBorderExtents = function(/*DomNode*/n, /*Object*/computedStyle){ - // summary: - // returns an object with properties useful for noting the border - // dimensions. - // - // * l/t = the sum of left/top border (respectively) - // * w = the sum of the left and right border - // * h = the sum of the top and bottom border - // - // The w/h are used for calculating boxes. - // Normally application code will not need to invoke this - // directly, and will use the ...box... functions instead. - var - ne = "none", - s = computedStyle||gcs(n), - bl = (s.borderLeftStyle != ne ? px(n, s.borderLeftWidth) : 0), - bt = (s.borderTopStyle != ne ? px(n, s.borderTopWidth) : 0); - return { - l: bl, - t: bt, - w: bl + (s.borderRightStyle!=ne ? px(n, s.borderRightWidth) : 0), - h: bt + (s.borderBottomStyle!=ne ? px(n, s.borderBottomWidth) : 0) - }; - } - - dojo._getPadBorderExtents = function(/*DomNode*/n, /*Object*/computedStyle){ - // summary: - // returns object with properties useful for box fitting with - // regards to padding. - // - // * l/t = the sum of left/top padding and left/top border (respectively) - // * w = the sum of the left and right padding and border - // * h = the sum of the top and bottom padding and border - // - // The w/h are used for calculating boxes. - // Normally application code will not need to invoke this - // directly, and will use the ...box... functions instead. - var - s = computedStyle||gcs(n), - p = d._getPadExtents(n, s), - b = d._getBorderExtents(n, s); - return { - l: p.l + b.l, - t: p.t + b.t, - w: p.w + b.w, - h: p.h + b.h - }; - } - - dojo._getMarginExtents = function(n, computedStyle){ - // summary: - // returns object with properties useful for box fitting with - // regards to box margins (i.e., the outer-box). - // - // * l/t = marginLeft, marginTop, respectively - // * w = total width, margin inclusive - // * h = total height, margin inclusive - // - // The w/h are used for calculating boxes. - // Normally application code will not need to invoke this - // directly, and will use the ...box... functions instead. - var - s = computedStyle||gcs(n), - l = px(n, s.marginLeft), - t = px(n, s.marginTop), - r = px(n, s.marginRight), - b = px(n, s.marginBottom); - if(d.isSafari && (s.position != "absolute")){ - // FIXME: Safari's version of the computed right margin - // is the space between our right edge and the right edge - // of our offsetParent. - // What we are looking for is the actual margin value as - // determined by CSS. - // Hack solution is to assume left/right margins are the same. - r = l; - } - return { - l: l, - t: t, - w: l+r, - h: t+b - }; - } - - // Box getters work in any box context because offsetWidth/clientWidth - // are invariant wrt box context - // - // They do *not* work for display: inline objects that have padding styles - // because the user agent ignores padding (it's bogus styling in any case) - // - // Be careful with IMGs because they are inline or block depending on - // browser and browser mode. - - // Although it would be easier to read, there are not separate versions of - // _getMarginBox for each browser because: - // 1. the branching is not expensive - // 2. factoring the shared code wastes cycles (function call overhead) - // 3. duplicating the shared code wastes bytes - - dojo._getMarginBox = function(/*DomNode*/node, /*Object*/computedStyle){ - // summary: - // returns an object that encodes the width, height, left and top - // positions of the node's margin box. - var s = computedStyle||gcs(node), me = d._getMarginExtents(node, s); - var l = node.offsetLeft - me.l, t = node.offsetTop - me.t; - if(d.isMoz){ - // Mozilla: - // If offsetParent has a computed overflow != visible, the offsetLeft is decreased - // by the parent's border. - // We don't want to compute the parent's style, so instead we examine node's - // computed left/top which is more stable. - var sl = parseFloat(s.left), st = parseFloat(s.top); - if(!isNaN(sl) && !isNaN(st)){ - l = sl, t = st; - }else{ - // If child's computed left/top are not parseable as a number (e.g. "auto"), we - // have no choice but to examine the parent's computed style. - var p = node.parentNode; - if(p && p.style){ - var pcs = gcs(p); - if(pcs.overflow != "visible"){ - var be = d._getBorderExtents(p, pcs); - l += be.l, t += be.t; - } - } - } - }else if(d.isOpera){ - // On Opera, offsetLeft includes the parent's border - var p = node.parentNode; - if(p){ - var be = d._getBorderExtents(p); - l -= be.l, t -= be.t; - } - } - return { - l: l, - t: t, - w: node.offsetWidth + me.w, - h: node.offsetHeight + me.h - }; - } - - dojo._getContentBox = function(node, computedStyle){ - // summary: - // Returns an object that encodes the width, height, left and top - // positions of the node's content box, irrespective of the - // current box model. - - // clientWidth/Height are important since the automatically account for scrollbars - // fallback to offsetWidth/Height for special cases (see #3378) - var s=computedStyle||gcs(node), pe=d._getPadExtents(node, s), be=d._getBorderExtents(node, s), w=node.clientWidth, h; - if(!w){ - w=node.offsetWidth, h=node.offsetHeight; - }else{ - h=node.clientHeight, be.w = be.h = 0; - } - // On Opera, offsetLeft includes the parent's border - if(d.isOpera){ pe.l += be.l; pe.t += be.t; }; - return { - l: pe.l, - t: pe.t, - w: w - pe.w - be.w, - h: h - pe.h - be.h - }; - } - - dojo._getBorderBox = function(node, computedStyle){ - var s=computedStyle||gcs(node), pe=d._getPadExtents(node, s), cb=d._getContentBox(node, s); - return { - l: cb.l - pe.l, - t: cb.t - pe.t, - w: cb.w + pe.w, - h: cb.h + pe.h - }; - } - - // Box setters depend on box context because interpretation of width/height styles - // vary wrt box context. - // - // The value of dojo.boxModel is used to determine box context. - // dojo.boxModel can be set directly to change behavior. - // - // Beware of display: inline objects that have padding styles - // because the user agent ignores padding (it's a bogus setup anyway) - // - // Be careful with IMGs because they are inline or block depending on - // browser and browser mode. - // - // Elements other than DIV may have special quirks, like built-in - // margins or padding, or values not detectable via computedStyle. - // In particular, margins on TABLE do not seems to appear - // at all in computedStyle on Mozilla. - - dojo._setBox = function(/*DomNode*/node, /*Number?*/l, /*Number?*/t, /*Number?*/w, /*Number?*/h, /*String?*/u){ - // summary: - // sets width/height/left/top in the current (native) box-model - // dimentions. Uses the unit passed in u. - // node: DOM Node reference. Id string not supported for performance reasons. - // l: optional. left offset from parent. - // t: optional. top offset from parent. - // w: optional. width in current box model. - // h: optional. width in current box model. - // u: optional. unit measure to use for other measures. Defaults to "px". - u = u || "px"; - var s = node.style; - if(!isNaN(l)){ s.left = l+u; } - if(!isNaN(t)){ s.top = t+u; } - if(w>=0){ s.width = w+u; } - if(h>=0){ s.height = h+u; } - } - - dojo._usesBorderBox = function(/*DomNode*/node){ - // summary: - // True if the node uses border-box layout. - - // We could test the computed style of node to see if a particular box - // has been specified, but there are details and we choose not to bother. - var n = node.tagName; - // For whatever reason, TABLE and BUTTON are always border-box by default. - // If you have assigned a different box to either one via CSS then - // box functions will break. - return d.boxModel=="border-box" || n=="TABLE" || n=="BUTTON"; // boolean - } - - dojo._setContentSize = function(/*DomNode*/node, /*Number*/widthPx, /*Number*/heightPx, /*Object*/computedStyle){ - // summary: - // Sets the size of the node's contents, irrespective of margins, - // padding, or borders. - if(d._usesBorderBox(node)){ - var pb = d._getPadBorderExtents(node, computedStyle); - if(widthPx >= 0){ widthPx += pb.w; } - if(heightPx >= 0){ heightPx += pb.h; } - } - d._setBox(node, NaN, NaN, widthPx, heightPx); - } - - dojo._setMarginBox = function(/*DomNode*/node, /*Number?*/leftPx, /*Number?*/topPx, - /*Number?*/widthPx, /*Number?*/heightPx, - /*Object*/computedStyle){ - // summary: - // sets the size of the node's margin box and placement - // (left/top), irrespective of box model. Think of it as a - // passthrough to dojo._setBox that handles box-model vagaries for - // you. - - var s = computedStyle||gcs(node); - // Some elements have special padding, margin, and box-model settings. - // To use box functions you may need to set padding, margin explicitly. - // Controlling box-model is harder, in a pinch you might set dojo.boxModel. - var bb=d._usesBorderBox(node), - pb=bb ? _nilExtents : d._getPadBorderExtents(node, s), - mb=d._getMarginExtents(node, s); - if(widthPx>=0){ widthPx = Math.max(widthPx - pb.w - mb.w, 0); } - if(heightPx>=0){ heightPx = Math.max(heightPx - pb.h - mb.h, 0); } - d._setBox(node, leftPx, topPx, widthPx, heightPx); - } - - var _nilExtents = { l:0, t:0, w:0, h:0 }; - - // public API - - dojo.marginBox = function(/*DomNode|String*/node, /*Object?*/box){ - // summary: - // Getter/setter for the margin-box of node. - // description: - // Returns an object in the expected format of box (regardless - // if box is passed). The object might look like: - // `{ l: 50, t: 200, w: 300: h: 150 }` - // for a node offset from its parent 50px to the left, 200px from - // the top with a margin width of 300px and a margin-height of - // 150px. - // node: - // id or reference to DOM Node to get/set box for - // box: - // If passed, denotes that dojo.marginBox() should - // update/set the margin box for node. Box is an object in the - // above format. All properties are optional if passed. - var n=d.byId(node), s=gcs(n), b=box; - return !b ? d._getMarginBox(n, s) : d._setMarginBox(n, b.l, b.t, b.w, b.h, s); // Object - } - - dojo.contentBox = function(/*DomNode|String*/node, /*Object?*/box){ - // summary: - // Getter/setter for the content-box of node. - // description: - // Returns an object in the expected format of box (regardless if box is passed). - // The object might look like: - // `{ l: 50, t: 200, w: 300: h: 150 }` - // for a node offset from its parent 50px to the left, 200px from - // the top with a content width of 300px and a content-height of - // 150px. Note that the content box may have a much larger border - // or margin box, depending on the box model currently in use and - // CSS values set/inherited for node. - // node: - // id or reference to DOM Node to get/set box for - // box: - // If passed, denotes that dojo.contentBox() should - // update/set the content box for node. Box is an object in the - // above format. All properties are optional if passed. - var n=dojo.byId(node), s=gcs(n), b=box; - return !b ? d._getContentBox(n, s) : d._setContentSize(n, b.w, b.h, s); // Object - } - - // ============================= - // Positioning - // ============================= - - var _sumAncestorProperties = function(node, prop){ - if(!(node = (node||0).parentNode)){return 0}; - var val, retVal = 0, _b = d.body(); - while(node && node.style){ - if(gcs(node).position == "fixed"){ - return 0; - } - val = node[prop]; - if(val){ - retVal += val - 0; - // opera and khtml #body & #html has the same values, we only - // need one value - if(node == _b){ break; } - } - node = node.parentNode; - } - return retVal; // integer - } - - dojo._docScroll = function(){ - var - _b = d.body(), - _w = d.global, - de = d.doc.documentElement; - return { - y: (_w.pageYOffset || de.scrollTop || _b.scrollTop || 0), - x: (_w.pageXOffset || d._fixIeBiDiScrollLeft(de.scrollLeft) || _b.scrollLeft || 0) - }; - }; - - dojo._isBodyLtr = function(){ - //FIXME: could check html and body tags directly instead of computed style? need to ignore case, accept empty values - return !("_bodyLtr" in d) ? - d._bodyLtr = gcs(d.body()).direction == "ltr" : - d._bodyLtr; // Boolean - } - - dojo._getIeDocumentElementOffset = function(){ - // summary - // The following values in IE contain an offset: - // event.clientX - // event.clientY - // node.getBoundingClientRect().left - // node.getBoundingClientRect().top - // But other position related values do not contain this offset, such as - // node.offsetLeft, node.offsetTop, node.style.left and node.style.top. - // The offset is always (2, 2) in LTR direction. When the body is in RTL - // direction, the offset counts the width of left scroll bar's width. - // This function computes the actual offset. - - //NOTE: assumes we're being called in an IE browser - - var de = d.doc.documentElement; - //FIXME: use this instead? var de = d.compatMode == "BackCompat" ? d.body : d.documentElement; - - return (d.isIE >= 7) ? - {x: de.getBoundingClientRect().left, y: de.getBoundingClientRect().top} - : - // IE 6.0 - {x: d._isBodyLtr() || window.parent == window ? - de.clientLeft : de.offsetWidth - de.clientWidth - de.clientLeft, - y: de.clientTop}; // Object - }; - - dojo._fixIeBiDiScrollLeft = function(/*Integer*/ scrollLeft){ - // In RTL direction, scrollLeft should be a negative value, but IE - // returns a positive one. All codes using documentElement.scrollLeft - // must call this function to fix this error, otherwise the position - // will offset to right when there is a horizontal scrollbar. - var dd = d.doc; - if(d.isIE && !dojo._isBodyLtr()){ - var de = dd.compatMode == "BackCompat" ? dd.body : dd.documentElement; - return scrollLeft + de.clientWidth - de.scrollWidth; // Integer - } - return scrollLeft; // Integer - } - - dojo._abs = function(/*DomNode*/node, /*Boolean?*/includeScroll){ - // summary: - // Gets the position of the passed element relative to - // the viewport (if includeScroll==false), or relative to the - // document root (if includeScroll==true). - // - // Returns an object of the form: - // { x: 100, y: 300 } - // if includeScroll is passed, the x and y values will include any - // document offsets that may affect the position relative to the - // viewport. - - // FIXME: need to decide in the brave-new-world if we're going to be - // margin-box or border-box. - var ownerDocument = node.ownerDocument; - var ret = { - x: 0, - y: 0 - }; - - // targetBoxType == "border-box" - var db = d.body(); - if(d.isIE || (d.isFF >= 3)){ - var client = node.getBoundingClientRect(); - var offset = (d.isIE) ? d._getIeDocumentElementOffset() : { x: 0, y: 0}; - ret.x = client.left - offset.x; - ret.y = client.top - offset.y; - }else if(ownerDocument["getBoxObjectFor"]){ - // mozilla - var bo = ownerDocument.getBoxObjectFor(node), - b = d._getBorderExtents(node); - ret.x = bo.x - b.l - _sumAncestorProperties(node, "scrollLeft"); - ret.y = bo.y - b.t - _sumAncestorProperties(node, "scrollTop"); - }else{ - if(node["offsetParent"]){ - var endNode; - // in Safari, if the node is an absolutely positioned child of - // the body and the body has a margin the offset of the child - // and the body contain the body's margins, so we need to end - // at the body - // FIXME: getting contrary results to the above in latest WebKit. - if(d.isSafari && - //(node.style.getPropertyValue("position") == "absolute") && - (gcs(node).position == "absolute") && - (node.parentNode == db)){ - endNode = db; - }else{ - endNode = db.parentNode; - } - if(node.parentNode != db){ - var nd = node; - if(d.isOpera){ nd = db; } - ret.x -= _sumAncestorProperties(nd, "scrollLeft"); - ret.y -= _sumAncestorProperties(nd, "scrollTop"); - } - var curnode = node; - do{ - var n = curnode.offsetLeft; - //FIXME: ugly hack to workaround the submenu in - //popupmenu2 does not shown up correctly in opera. - //Someone have a better workaround? - if(!d.isOpera || n > 0){ - ret.x += isNaN(n) ? 0 : n; - } - var t = curnode.offsetTop; - ret.y += isNaN(t) ? 0 : t; - if(d.isSafari && curnode != node){ - var cs = gcs(curnode); - ret.x += px(curnode, cs.borderLeftWidth); - ret.y += px(curnode, cs.borderTopWidth); - } - curnode = curnode.offsetParent; - }while((curnode != endNode) && curnode); - }else if(node.x && node.y){ - ret.x += isNaN(node.x) ? 0 : node.x; - ret.y += isNaN(node.y) ? 0 : node.y; - } - } - // account for document scrolling - // if offsetParent is used, ret value already includes scroll position - // so we may have to actually remove that value if !includeScroll - if(includeScroll){ - var scroll = d._docScroll(); - ret.y += scroll.y; - ret.x += scroll.x; - } - - return ret; // object - } - - // FIXME: need a setter for coords or a moveTo!! - dojo.coords = function(/*DomNode|String*/node, /*Boolean?*/includeScroll){ - // summary: - // Returns an object that measures margin box width/height and - // absolute positioning data from dojo._abs(). - // - // description: - // Returns an object that measures margin box width/height and - // absolute positioning data from dojo._abs(). - // Return value will be in the form: - // `{ l: 50, t: 200, w: 300: h: 150, x: 100, y: 300 }` - // Does not act as a setter. If includeScroll is passed, the x and - // y params are affected as one would expect in dojo._abs(). - var n=d.byId(node), s=gcs(n), mb=d._getMarginBox(n, s); - var abs = d._abs(n, includeScroll); - mb.x = abs.x; - mb.y = abs.y; - return mb; - } - - // ============================= - // Element attribute Functions - // ============================= - - var _fixAttrName = function(/*String*/name){ - switch(name.toLowerCase()){ - case "tabindex": - // Internet Explorer will only set or remove tabindex - // if it is spelled "tabIndex" - // console.debug((dojo.isIE && dojo.isIE < 8)? "tabIndex" : "tabindex"); - return (d.isIE && d.isIE < 8) ? "tabIndex" : "tabindex"; - default: - return name; - } - } - - // non-deprecated HTML4 attributes with default values - // http://www.w3.org/TR/html401/index/attributes.html - // FF and Safari will return the default values if you - // access the attributes via a property but not - // via getAttribute() - var _attrProps = { - colspan: "colSpan", - enctype: "enctype", - frameborder: "frameborder", - method: "method", - rowspan: "rowSpan", - scrolling: "scrolling", - shape: "shape", - span: "span", - type: "type", - valuetype: "valueType" - } - - dojo.hasAttr = function(/*DomNode|String*/node, /*String*/name){ - // summary: - // Returns true if the requested attribute is specified on the - // given element, and false otherwise. - // node: - // id or reference to the element to check - // name: - // the name of the attribute - // returns: - // true if the requested attribute is specified on the - // given element, and false otherwise - var attr = d.byId(node).getAttributeNode(_fixAttrName(name)); - return attr ? attr.specified : false; // Boolean - } - - var _evtHdlrMap = { - - } - - var _ctr = 0; - var _attrId = dojo._scopeName + "attrid"; - - dojo.attr = function(/*DomNode|String*/node, /*String|Object*/name, /*String?*/value){ - // summary: - // Gets or sets an attribute on an HTML element. - // description: - // Handles normalized getting and setting of attributes on DOM - // Nodes. If 2 arguments are passed, and a the second argumnt is a - // string, acts as a getter. - // - // If a third argument is passed, or if the second argumnt is a - // map of attributes, acts as a setter. - // - // When passing functions as values, note that they will not be - // directly assigned to slots on the node, but rather the default - // behavior will be removed and the new behavior will be added - // using `dojo.connect()`, meaning that event handler properties - // will be normalized and that some caveats with regards to - // non-standard behaviors for onsubmit apply. Namely that you - // should cancel form submission using `dojo.stopEvent()` on the - // passed event object instead of returning a boolean value from - // the handler itself. - // node: - // id or reference to the element to get or set the attribute on - // name: - // the name of the attribute to get or set. - // value: - // The value to set for the attribute - // returns: - // when used as a getter, the value of the requested attribute - // or null if that attribute does not have a specified or - // default value; - // - // when user as a setter, undefined - // example: - // | // get the current value of the "foo" attribute on a node - // | dojo.attr(dojo.byId("nodeId"), "foo"); - // | - // | // we can just pass the id: - // | dojo.attr("nodeId", "foo"); - // | - // | // use attr() to set the tab index - // | dojo.attr("nodeId", "tabindex", 3); - // | - // | // set multiple values at once, including event handlers: - // | dojo.attr("formId", { - // | "foo": "bar", - // | "tabindex": -1, - // | "method": "POST", - // | "onsubmit": function(e){ - // | // stop submitting the form. Note that the IE behavior - // | // of returning true or false will have no effect here - // | // since our handler is connect()ed to the built-in - // | // onsubmit behavior and so we need to use - // | // dojo.stopEvent() to ensure that the submission - // | // doesn't proceed. - // | dojo.stopEvent(e); - // | - // | // submit the form with Ajax - // | dojo.xhrPost({ form: "formId" }); - // | } - // | }); - - var args = arguments.length; - if(args == 2 && !d.isString(name)){ - for(var x in name){ d.attr(node, x, name[x]); } - return; - } - node = d.byId(node); - name = _fixAttrName(name); - if(args == 3){ - if(d.isFunction(value)){ - // clobber if we can - var attrId = d.attr(node, _attrId); - if(!attrId){ - attrId = _ctr++; - d.attr(node, _attrId, attrId); - } - if(!_evtHdlrMap[attrId]){ - _evtHdlrMap[attrId] = {}; - } - var h = _evtHdlrMap[attrId][name]; - if(h){ - d.disconnect(h); - }else{ - try{ - delete node[name]; - }catch(e){} - } - - // ensure that event objects are normalized, etc. - _evtHdlrMap[attrId][name] = d.connect(node, name, value); - - }else if(typeof value == "boolean"){ // e.g. onsubmit, disabled - // if a function, we should normalize the event object here!!! - node[name] = value; - }else{ - node.setAttribute(name, value); - } - return; - }else{ - // should we access this attribute via a property or - // via getAttribute()? - var prop = _attrProps[name.toLowerCase()]; - if(prop){ - return node[prop]; - }else{ - var value = node[name]; - return (typeof value == 'boolean' || typeof value == 'function') ? value : (d.hasAttr(node, name) ? node.getAttribute(name) : null); - } - } - } - - dojo.removeAttr = function(/*DomNode|String*/node, /*String*/name){ - // summary: - // Removes an attribute from an HTML element. - // node: - // id or reference to the element to remove the attribute from - // name: - // the name of the attribute to remove - d.byId(node).removeAttribute(_fixAttrName(name)); - } -})(); - -// ============================= -// (CSS) Class Functions -// ============================= - -dojo.hasClass = function(/*DomNode|String*/node, /*String*/classStr){ - // summary: - // Returns whether or not the specified classes are a portion of the - // class list currently applied to the node. - return ((" "+dojo.byId(node).className+" ").indexOf(" "+classStr+" ") >= 0); // Boolean -}; - -dojo.addClass = function(/*DomNode|String*/node, /*String*/classStr){ - // summary: - // Adds the specified classes to the end of the class list on the - // passed node. - node = dojo.byId(node); - var cls = node.className; - if((" "+cls+" ").indexOf(" "+classStr+" ") < 0){ - node.className = cls + (cls ? ' ' : '') + classStr; - } -}; - -dojo.removeClass = function(/*DomNode|String*/node, /*String*/classStr){ - // summary: Removes the specified classes from node. - node = dojo.byId(node); - var t = dojo.trim((" " + node.className + " ").replace(" " + classStr + " ", " ")); - if(node.className != t){ node.className = t; } -}; - -dojo.toggleClass = function(/*DomNode|String*/node, /*String*/classStr, /*Boolean?*/condition){ - // summary: - // Adds a class to node if not present, or removes if present. - // Pass a boolean condition if you want to explicitly add or remove. - // condition: - // If passed, true means to add the class, false means to remove. - if(condition === undefined){ - condition = !dojo.hasClass(node, classStr); - } - dojo[condition ? "addClass" : "removeClass"](node, classStr); -}; - -} - -if(!dojo._hasResource["dojo._base.NodeList"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.NodeList"] = true; -dojo.provide("dojo._base.NodeList"); - - - -(function(){ - - var d = dojo; - - var tnl = function(arr){ - // decorate an array to make it look like a NodeList - arr.constructor = dojo.NodeList; - dojo._mixin(arr, dojo.NodeList.prototype); - return arr; - } - - var _mapIntoDojo = function(func, alwaysThis){ - // returns a function which, when executed in the scope of its caller, - // applies the passed arguments to a particular dojo.* function (named - // in func) and aggregates the returns. if alwaysThis is true, it - // always returns the scope object and not the collected returns from - // the Dojo method - return function(){ - var _a = arguments; - var aa = d._toArray(_a, 0, [null]); - var s = this.map(function(i){ - aa[0] = i; - return d[func].apply(d, aa); - }); - return (alwaysThis || ( (_a.length > 1) || !d.isString(_a[0]) )) ? this : s; // String||dojo.NodeList - } - }; - - dojo.NodeList = function(){ - // summary: - // dojo.NodeList is as subclass of Array which adds syntactic - // sugar for chaining, common iteration operations, animation, - // and node manipulation. NodeLists are most often returned as - // the result of dojo.query() calls. - // example: - // create a node list from a node - // | new dojo.NodeList(dojo.byId("foo")); - - return tnl(Array.apply(null, arguments)); - } - - dojo.NodeList._wrap = tnl; - - dojo.extend(dojo.NodeList, { - // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array#Methods - - // FIXME: handle return values for #3244 - // http://trac.dojotoolkit.org/ticket/3244 - - // FIXME: - // need to wrap or implement: - // join (perhaps w/ innerHTML/outerHTML overload for toString() of items?) - // reduce - // reduceRight - - slice: function(/*===== begin, end =====*/){ - // summary: - // Returns a new NodeList, maintaining this one in place - // description: - // This method behaves exactly like the Array.slice method - // with the caveat that it returns a dojo.NodeList and not a - // raw Array. For more details, see: - // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:slice - // begin: Integer - // Can be a positive or negative integer, with positive - // integers noting the offset to begin at, and negative - // integers denoting an offset from the end (i.e., to the left - // of the end) - // end: Integer? - // Optional parameter to describe what position relative to - // the NodeList's zero index to end the slice at. Like begin, - // can be positive or negative. - var a = dojo._toArray(arguments); - return tnl(a.slice.apply(this, a)); - }, - - splice: function(/*===== index, howmany, item =====*/){ - // summary: - // Returns a new NodeList, manipulating this NodeList based on - // the arguments passed, potentially splicing in new elements - // at an offset, optionally deleting elements - // description: - // This method behaves exactly like the Array.splice method - // with the caveat that it returns a dojo.NodeList and not a - // raw Array. For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:splice> - // index: Integer - // begin can be a positive or negative integer, with positive - // integers noting the offset to begin at, and negative - // integers denoting an offset from the end (i.e., to the left - // of the end) - // howmany: Integer? - // Optional parameter to describe what position relative to - // the NodeList's zero index to end the slice at. Like begin, - // can be positive or negative. - // item: Object...? - // Any number of optional parameters may be passed in to be - // spliced into the NodeList - // returns: - // dojo.NodeList - var a = dojo._toArray(arguments); - return tnl(a.splice.apply(this, a)); - }, - - concat: function(/*===== item =====*/){ - // summary: - // Returns a new NodeList comprised of items in this NodeList - // as well as items passed in as parameters - // description: - // This method behaves exactly like the Array.concat method - // with the caveat that it returns a dojo.NodeList and not a - // raw Array. For more details, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:concat> - // item: Object...? - // Any number of optional parameters may be passed in to be - // spliced into the NodeList - // returns: - // dojo.NodeList - var a = dojo._toArray(arguments, 0, [this]); - return tnl(a.concat.apply([], a)); - }, - - indexOf: function(/*Object*/ value, /*Integer?*/ fromIndex){ - // summary: - // see dojo.indexOf(). The primary difference is that the acted-on - // array is implicitly this NodeList - // value: - // The value to search for. - // fromIndex: - // The loction to start searching from. Optional. Defaults to 0. - // description: - // For more details on the behavior of indexOf, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:indexOf> - // returns: - // Positive Integer or 0 for a match, -1 of not found. - return d.indexOf(this, value, fromIndex); // Integer - }, - - lastIndexOf: function(/*===== value, fromIndex =====*/){ - // summary: - // see dojo.lastIndexOf(). The primary difference is that the - // acted-on array is implicitly this NodeList - // description: - // For more details on the behavior of lastIndexOf, see: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:lastIndexOf> - // value: Object - // The value to search for. - // fromIndex: Integer? - // The loction to start searching from. Optional. Defaults to 0. - // returns: - // Positive Integer or 0 for a match, -1 of not found. - return d.lastIndexOf.apply(d, d._toArray(arguments, 0, [this])); // Integer - }, - - every: function(/*Function*/callback, /*Object?*/thisObject){ - // summary: - // see `dojo.every()` and: - // <http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:every> - // Takes the same structure of arguments and returns as - // dojo.every() with the caveat that the passed array is - // implicitly this NodeList - return d.every(this, callback, thisObject); // Boolean - }, - - some: function(/*Function*/callback, /*Object?*/thisObject){ - // summary: - // see dojo.some() and: - // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:some - // Takes the same structure of arguments and returns as - // dojo.some() with the caveat that the passed array is - // implicitly this NodeList - return d.some(this, callback, thisObject); // Boolean - }, - - map: function(/*Function*/ func, /*Function?*/ obj){ - // summary: - // see dojo.map(). The primary difference is that the acted-on - // array is implicitly this NodeList and the return is a - // dojo.NodeList (a subclass of Array) - - return d.map(this, func, obj, d.NodeList); // dojo.NodeList - }, - - forEach: function(callback, thisObj){ - // summary: - // see dojo.forEach(). The primary difference is that the acted-on - // array is implicitly this NodeList - - d.forEach(this, callback, thisObj); - // non-standard return to allow easier chaining - return this; // dojo.NodeList - }, - - // custom methods - - coords: function(){ - // summary: - // Returns the box objects all elements in a node list as - // an Array (*not* a NodeList) - - return d.map(this, d.coords); // Array - }, - - /*===== - attr: function(property, value){ - // summary: - // gets or sets the DOM attribute for every element in the - // NodeList - // property: String - // the attribute to get/set - // value: String? - // optional. The value to set the property to - // return: - // if no value is passed, the result is an array of attribute values - // If a value is passed, the return is this NodeList - }, - - style: function(property, value){ - // summary: - // gets or sets the CSS property for every element in the NodeList - // property: String - // the CSS property to get/set, in JavaScript notation - // ("lineHieght" instead of "line-height") - // value: String? - // optional. The value to set the property to - // return: - // if no value is passed, the result is an array of strings. - // If a value is passed, the return is this NodeList - }, - - addClass: function(className){ - // summary: - // adds the specified class to every node in the list - // className: String - // the CSS class to add - // return: - // dojo.NodeList, this list - }, - - removeClass: function(className){ - // summary: - // removes the specified class from every node in the list - // className: String - // the CSS class to add - // return: - // dojo.NodeList, this list - }, - - toggleClass: function(className, condition){ - // summary: - // Adds a class to node if not present, or removes if present. - // Pass a boolean condition if you want to explicitly add or remove. - // condition: Boolean? - // If passed, true means to add the class, false means to remove. - // className: String - // the CSS class to add - // return: dojo.NodeList - // this list - }, - - connect: function(methodName, objOrFunc, funcName){ - // summary: - // attach event handlers to every item of the NodeList. Uses dojo.connect() - // so event properties are normalized - // methodName: String - // the name of the method to attach to. For DOM events, this should be - // the lower-case name of the event - // objOrFunc: Object|Function|String - // if 2 arguments are passed (methodName, objOrFunc), objOrFunc should - // reference a function or be the name of the function in the global - // namespace to attach. If 3 arguments are provided - // (methodName, objOrFunc, funcName), objOrFunc must be the scope to - // locate the bound function in - // funcName: String? - // optional. A string naming the function in objOrFunc to bind to the - // event. May also be a function reference. - // example: - // add an onclick handler to every button on the page - // | dojo.query("div:nth-child(odd)").connect("onclick", function(e){ - // | console.debug("clicked!"); - // | }); - // example: - // attach foo.bar() to every odd div's onmouseover - // | dojo.query("div:nth-child(odd)").connect("onmouseover", foo, "bar"); - }, - =====*/ - attr: _mapIntoDojo("attr"), - style: _mapIntoDojo("style"), - addClass: _mapIntoDojo("addClass", true), - removeClass: _mapIntoDojo("removeClass", true), - toggleClass: _mapIntoDojo("toggleClass", true), - connect: _mapIntoDojo("connect", true), - - // FIXME: connectPublisher()? connectRunOnce()? - - place: function(/*String||Node*/ queryOrNode, /*String*/ position){ - // summary: - // places elements of this node list relative to the first element matched - // by queryOrNode. Returns the original NodeList. - // queryOrNode: - // may be a string representing any valid CSS3 selector or a DOM node. - // In the selector case, only the first matching element will be used - // for relative positioning. - // position: - // can be one of: - // * "last"||"end" (default) - // * "first||"start" - // * "before" - // * "after" - // or an offset in the childNodes property - var item = d.query(queryOrNode)[0]; - return this.forEach(function(i){ d.place(i, item, (position||"last")); }); // dojo.NodeList - }, - - orphan: function(/*String?*/ simpleFilter){ - // summary: - // removes elements in this list that match the simple - // filter from their parents and returns them as a new - // NodeList. - // simpleFilter: - // single-expression CSS filter - // return: - // `dojo.NodeList` the orpahned elements - var orphans = simpleFilter ? d._filterQueryResult(this, simpleFilter) : this; - orphans.forEach(function(item){ - if(item.parentNode){ - item.parentNode.removeChild(item); - } - }); - return orphans; // dojo.NodeList - }, - - adopt: function(/*String||Array||DomNode*/ queryOrListOrNode, /*String?*/ position){ - // summary: - // places any/all elements in queryOrListOrNode at a - // position relative to the first element in this list. - // Returns a dojo.NodeList of the adopted elements. - // queryOrListOrNode: - // a DOM node or a query string or a query result. - // Represents the nodes to be adopted relative to the - // first element of this NodeList. - // position: - // can be one of: - // * "last"||"end" (default) - // * "first||"start" - // * "before" - // * "after" - // or an offset in the childNodes property - var item = this[0]; - return d.query(queryOrListOrNode).forEach(function(ai){ d.place(ai, item, position || "last"); }); // dojo.NodeList - }, - - // FIXME: do we need this? - query: function(/*String*/ queryStr){ - // summary: - // Returns a new, flattened NodeList. Elements of the new list - // satisfy the passed query but use elements of the - // current NodeList as query roots. - - if(!queryStr){ return this; } - - // FIXME: probably slow - // FIXME: use map? - var ret = d.NodeList(); - this.forEach(function(item){ - d.query(queryStr, item).forEach(function(subItem){ - if(subItem !== undefined){ - ret.push(subItem); - } - }); - }); - return ret; // dojo.NodeList - }, - - filter: function(/*String*/ simpleQuery){ - // summary: - // "masks" the built-in javascript filter() method to support - // passing a simple string filter in addition to supporting - // filtering function objects. - // example: - // "regular" JS filter syntax as exposed in dojo.filter: - // | dojo.query("*").filter(function(item){ - // | // highlight every paragraph - // | return (item.nodeName == "p"); - // | }).styles("backgroundColor", "yellow"); - // example: - // the same filtering using a CSS selector - // | dojo.query("*").filter("p").styles("backgroundColor", "yellow"); - - var items = this; - var _a = arguments; - var r = d.NodeList(); - var rp = function(t){ - if(t !== undefined){ - r.push(t); - } - } - if(d.isString(simpleQuery)){ - items = d._filterQueryResult(this, _a[0]); - if(_a.length == 1){ - // if we only got a string query, pass back the filtered results - return items; // dojo.NodeList - } - // if we got a callback, run it over the filtered items - _a.shift(); - } - // handle the (callback, [thisObject]) case - d.forEach(d.filter(items, _a[0], _a[1]), rp); - return r; // dojo.NodeList - }, - - /* - // FIXME: should this be "copyTo" and include parenting info? - clone: function(){ - // summary: - // creates node clones of each element of this list - // and returns a new list containing the clones - }, - */ - - addContent: function(/*String*/ content, /*String||Integer?*/ position){ - // summary: - // add a node or some HTML as a string to every item in the list. - // Returns the original list. - // description: - // a copy of the HTML content is added to each item in the - // list, with an optional position argument. If no position - // argument is provided, the content is appended to the end of - // each item. - // content: - // the HTML in string format to add at position to every item - // position: - // can be one of: - // * "last"||"end" (default) - // * "first||"start" - // * "before" - // * "after" - // or an offset in the childNodes property - // example: - // appends content to the end if the position is ommitted - // | dojo.query("h3 > p").addContent("hey there!"); - // example: - // add something to the front of each element that has a "thinger" property: - // | dojo.query("[thinger]").addContent("...", "first"); - // example: - // adds a header before each element of the list - // | dojo.query(".note").addContent("<h4>NOTE:</h4>", "before"); - var ta = d.doc.createElement("span"); - if(d.isString(content)){ - ta.innerHTML = content; - }else{ - ta.appendChild(content); - } - if(position === undefined){ - position = "last"; - } - var ct = (position == "first" || position == "after") ? "lastChild" : "firstChild"; - this.forEach(function(item){ - var tn = ta.cloneNode(true); - while(tn[ct]){ - d.place(tn[ct], item, position); - } - }); - return this; // dojo.NodeList - }, - - empty: function(){ - // summary: - // clears all content from each node in the list - return this.forEach("item.innerHTML='';"); // dojo.NodeList - - // FIXME: should we be checking for and/or disposing of widgets below these nodes? - }, - - instantiate: function(/*String|Object*/ declaredClass, /*Object?*/ properties){ - // summary: - // Create a new instance of a specified class, using the - // specified properties and each node in the nodeList as a - // srcNodeRef - // - var c = d.isFunction(declaredClass) ? declaredClass : d.getObject(declaredClass); - return this.forEach(function(i){ - new c(properties||{},i); - }) // dojo.NodeList - } - - }); - - // syntactic sugar for DOM events - d.forEach([ - "blur", "focus", "click", "keydown", "keypress", "keyup", "mousedown", - "mouseenter", "mouseleave", "mousemove", "mouseout", "mouseover", - "mouseup" - ], function(evt){ - var _oe = "on"+evt; - dojo.NodeList.prototype[_oe] = function(a, b){ - return this.connect(_oe, a, b); - } - // FIXME: should these events trigger publishes? - /* - return (a ? this.connect(_oe, a, b) : - this.forEach(function(n){ - // FIXME: - // listeners get buried by - // addEventListener and can't be dug back - // out to be triggered externally. - // see: - // http://developer.mozilla.org/en/docs/DOM:element - - console.debug(n, evt, _oe); - - // FIXME: need synthetic event support! - var _e = { target: n, faux: true, type: evt }; - // dojo._event_listener._synthesizeEvent({}, { target: n, faux: true, type: evt }); - try{ n[evt](_e); }catch(e){ console.debug(e); } - try{ n[_oe](_e); }catch(e){ console.debug(e); } - }) - ); - } - */ - } - ); - -})(); - -} - -if(!dojo._hasResource["dojo._base.query"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.query"] = true; -dojo.provide("dojo._base.query"); - - -/* - dojo.query() architectural overview: - - dojo.query is a relatively full-featured CSS3 query library. It is - designed to take any valid CSS3 selector and return the nodes matching - the selector. To do this quickly, it processes queries in several - steps, applying caching where profitable. - - The steps (roughly in reverse order of the way they appear in the code): - 1.) check to see if we already have a "query dispatcher" - - if so, use that with the given parameterization. Skip to step 4. - 2.) attempt to determine which branch to dispatch the query to: - - JS (optimized DOM iteration) - - xpath (for browsers that support it and where it's fast) - - native (not available in any browser yet) - 3.) tokenize and convert to executable "query dispatcher" - - this is where the lion's share of the complexity in the - system lies. In the DOM version, the query dispatcher is - assembled as a chain of "yes/no" test functions pertaining to - a section of a simple query statement (".blah:nth-child(odd)" - but not "div div", which is 2 simple statements). Individual - statement dispatchers are cached (to prevent re-definition) - as are entire dispatch chains (to make re-execution of the - same query fast) - - in the xpath path, tokenization yeilds a concatenation of - parameterized xpath selectors. As with the DOM version, both - simple selector blocks and overall evaluators are cached to - prevent re-defintion - 4.) the resulting query dispatcher is called in the passed scope (by default the top-level document) - - for DOM queries, this results in a recursive, top-down - evaluation of nodes based on each simple query section - - xpath queries can, thankfully, be executed in one shot - 5.) matched nodes are pruned to ensure they are unique -*/ - -;(function(){ - // define everything in a closure for compressability reasons. "d" is an - // alias to "dojo" since it's so frequently used. This seems a - // transformation that the build system could perform on a per-file basis. - - //////////////////////////////////////////////////////////////////////// - // Utility code - //////////////////////////////////////////////////////////////////////// - - var d = dojo; - var childNodesName = dojo.isIE ? "children" : "childNodes"; - var caseSensitive = false; - - var getQueryParts = function(query){ - // summary: state machine for query tokenization - if(">~+".indexOf(query.charAt(query.length-1)) >= 0){ - query += " *" - } - query += " "; // ensure that we terminate the state machine - - var ts = function(s, e){ - return d.trim(query.slice(s, e)); - } - - // the overall data graph of the full query, as represented by queryPart objects - var qparts = []; - // state keeping vars - var inBrackets = -1; - var inParens = -1; - var inMatchFor = -1; - var inPseudo = -1; - var inClass = -1; - var inId = -1; - var inTag = -1; - var lc = ""; // the last character - var cc = ""; // the current character - var pStart; - // iteration vars - var x = 0; // index in the query - var ql = query.length; - var currentPart = null; // data structure representing the entire clause - var _cp = null; // the current pseudo or attr matcher - - var endTag = function(){ - if(inTag >= 0){ - var tv = (inTag == x) ? null : ts(inTag, x).toLowerCase(); - currentPart[ (">~+".indexOf(tv) < 0) ? "tag" : "oper" ] = tv; - inTag = -1; - } - } - - var endId = function(){ - if(inId >= 0){ - currentPart.id = ts(inId, x).replace(/\\/g, ""); - inId = -1; - } - } - - var endClass = function(){ - if(inClass >= 0){ - currentPart.classes.push(ts(inClass+1, x).replace(/\\/g, "")); - inClass = -1; - } - } - - var endAll = function(){ - endId(); endTag(); endClass(); - } - - for(; lc=cc, cc=query.charAt(x),x<ql; x++){ - if(lc == "\\"){ continue; } - if(!currentPart){ - // NOTE: I hate all this alloc, but it's shorter than writing tons of if's - pStart = x; - currentPart = { - query: null, - pseudos: [], - attrs: [], - classes: [], - tag: null, - oper: null, - id: null - }; - inTag = x; - } - - if(inBrackets >= 0){ - // look for a the close first - if(cc == "]"){ - if(!_cp.attr){ - _cp.attr = ts(inBrackets+1, x); - }else{ - _cp.matchFor = ts((inMatchFor||inBrackets+1), x); - } - var cmf = _cp.matchFor; - if(cmf){ - if( (cmf.charAt(0) == '"') || (cmf.charAt(0) == "'") ){ - _cp.matchFor = cmf.substring(1, cmf.length-1); - } - } - currentPart.attrs.push(_cp); - _cp = null; // necessaray? - inBrackets = inMatchFor = -1; - }else if(cc == "="){ - var addToCc = ("|~^$*".indexOf(lc) >=0 ) ? lc : ""; - _cp.type = addToCc+cc; - _cp.attr = ts(inBrackets+1, x-addToCc.length); - inMatchFor = x+1; - } - // now look for other clause parts - }else if(inParens >= 0){ - if(cc == ")"){ - if(inPseudo >= 0){ - _cp.value = ts(inParens+1, x); - } - inPseudo = inParens = -1; - } - }else if(cc == "#"){ - endAll(); - inId = x+1; - }else if(cc == "."){ - endAll(); - inClass = x; - }else if(cc == ":"){ - endAll(); - inPseudo = x; - }else if(cc == "["){ - endAll(); - inBrackets = x; - _cp = { - /*===== - attr: null, type: null, matchFor: null - =====*/ - }; - }else if(cc == "("){ - if(inPseudo >= 0){ - _cp = { - name: ts(inPseudo+1, x), - value: null - } - currentPart.pseudos.push(_cp); - } - inParens = x; - }else if(cc == " " && lc != cc){ - // note that we expect the string to be " " terminated - endAll(); - if(inPseudo >= 0){ - currentPart.pseudos.push({ name: ts(inPseudo+1, x) }); - } - currentPart.hasLoops = ( - currentPart.pseudos.length || - currentPart.attrs.length || - currentPart.classes.length ); - currentPart.query = ts(pStart, x); - currentPart.tag = (currentPart["oper"]) ? null : (currentPart.tag || "*"); - qparts.push(currentPart); - currentPart = null; - } - } - return qparts; - }; - - - //////////////////////////////////////////////////////////////////////// - // XPath query code - //////////////////////////////////////////////////////////////////////// - - // this array is a lookup used to generate an attribute matching function. - // There is a similar lookup/generator list for the DOM branch with similar - // calling semantics. - var xPathAttrs = { - "*=": function(attr, value){ - return "[contains(@"+attr+", '"+ value +"')]"; - }, - "^=": function(attr, value){ - return "[starts-with(@"+attr+", '"+ value +"')]"; - }, - "$=": function(attr, value){ - return "[substring(@"+attr+", string-length(@"+attr+")-"+(value.length-1)+")='"+value+"']"; - }, - "~=": function(attr, value){ - return "[contains(concat(' ',@"+attr+",' '), ' "+ value +" ')]"; - }, - "|=": function(attr, value){ - return "[contains(concat(' ',@"+attr+",' '), ' "+ value +"-')]"; - }, - "=": function(attr, value){ - return "[@"+attr+"='"+ value +"']"; - } - }; - - // takes a list of attribute searches, the overall query, a function to - // generate a default matcher, and a closure-bound method for providing a - // matching function that generates whatever type of yes/no distinguisher - // the query method needs. The method is a bit tortured and hard to read - // because it needs to be used in both the XPath and DOM branches. - var handleAttrs = function( attrList, - query, - getDefault, - handleMatch){ - d.forEach(query.attrs, function(attr){ - var matcher; - // type, attr, matchFor - if(attr.type && attrList[attr.type]){ - matcher = attrList[attr.type](attr.attr, attr.matchFor); - }else if(attr.attr.length){ - matcher = getDefault(attr.attr); - } - if(matcher){ handleMatch(matcher); } - }); - } - - var buildPath = function(query){ - var xpath = "."; - var qparts = getQueryParts(d.trim(query)); - while(qparts.length){ - var tqp = qparts.shift(); - var prefix; - var postfix = ""; - if(tqp.oper == ">"){ - prefix = "/"; - // prefix = "/child::*"; - tqp = qparts.shift(); - }else if(tqp.oper == "~"){ - prefix = "/following-sibling::"; // get element following siblings - tqp = qparts.shift(); - }else if(tqp.oper == "+"){ - // FIXME: - // fails when selecting subsequent siblings by node type - // because the position() checks the position in the list - // of matching elements and not the localized siblings - prefix = "/following-sibling::"; - postfix = "[position()=1]"; - tqp = qparts.shift(); - }else{ - prefix = "//"; - // prefix = "/descendant::*" - } - - // get the tag name (if any) - - xpath += prefix + tqp.tag + postfix; - - // check to see if it's got an id. Needs to come first in xpath. - if(tqp.id){ - xpath += "[@id='"+tqp.id+"'][1]"; - } - - d.forEach(tqp.classes, function(cn){ - var cnl = cn.length; - var padding = " "; - if(cn.charAt(cnl-1) == "*"){ - padding = ""; cn = cn.substr(0, cnl-1); - } - xpath += - "[contains(concat(' ',@class,' '), ' "+ - cn + padding + "')]"; - }); - - handleAttrs(xPathAttrs, tqp, - function(condition){ - return "[@"+condition+"]"; - }, - function(matcher){ - xpath += matcher; - } - ); - - // FIXME: need to implement pseudo-class checks!! - }; - return xpath; - }; - - var _xpathFuncCache = {}; - var getXPathFunc = function(path){ - if(_xpathFuncCache[path]){ - return _xpathFuncCache[path]; - } - - var doc = d.doc; - // don't need to memoize. The closure scope handles it for us. - var xpath = buildPath(path); - - var tf = function(parent){ - // XPath query strings are memoized. - var ret = []; - var xpathResult; - try{ - xpathResult = doc.evaluate(xpath, parent, null, - // XPathResult.UNORDERED_NODE_ITERATOR_TYPE, null); - XPathResult.ANY_TYPE, null); - }catch(e){ - console.debug("failure in exprssion:", xpath, "under:", parent); - console.debug(e); - } - var result = xpathResult.iterateNext(); - while(result){ - ret.push(result); - result = xpathResult.iterateNext(); - } - return ret; - } - return _xpathFuncCache[path] = tf; - }; - - /* - d.xPathMatch = function(query){ - // XPath based DOM query system. Handles a small subset of CSS - // selectors, subset is identical to the non-XPath version of this - // function. - - return getXPathFunc(query)(); - } - */ - - //////////////////////////////////////////////////////////////////////// - // DOM query code - //////////////////////////////////////////////////////////////////////// - - var _filtersCache = {}; - var _simpleFiltersCache = {}; - - // the basic building block of the yes/no chaining system. agree(f1, f2) - // generates a new function which returns the boolean results of both of - // the passed functions to a single logical-anded result. - var agree = function(first, second){ - if(!first){ return second; } - if(!second){ return first; } - - return function(){ - return first.apply(window, arguments) && second.apply(window, arguments); - } - } - - var _childElements = function(root){ - var ret = []; - var te, x=0, tret = root[childNodesName]; - while(te=tret[x++]){ - if(te.nodeType == 1){ ret.push(te); } - } - return ret; - } - - var _nextSiblings = function(root, single){ - var ret = []; - var te = root; - while(te = te.nextSibling){ - if(te.nodeType == 1){ - ret.push(te); - if(single){ break; } - } - } - return ret; - } - - var _filterDown = function(element, queryParts, matchArr, idx){ - // NOTE: - // in the fast path! this function is called recursively and for - // every run of a query. - var nidx = idx+1; - var isFinal = (queryParts.length == nidx); - var tqp = queryParts[idx]; - - // see if we can constrain our next level to direct children - if(tqp.oper){ - var ecn = (tqp.oper == ">") ? - _childElements(element) : - _nextSiblings(element, (tqp.oper == "+")); - - if(!ecn || !ecn.length){ - return; - } - nidx++; - isFinal = (queryParts.length == nidx); - // kinda janky, too much array alloc - var tf = getFilterFunc(queryParts[idx+1]); - // for(var x=ecn.length-1, te; x>=0, te=ecn[x]; x--){ - for(var x=0, ecnl=ecn.length, te; x<ecnl, te=ecn[x]; x++){ - if(tf(te)){ - if(isFinal){ - matchArr.push(te); - }else{ - _filterDown(te, queryParts, matchArr, nidx); - } - } - /* - if(x==0){ - break; - } - */ - } - } - - // otherwise, keep going down, unless we'er at the end - var candidates = getElementsFunc(tqp)(element); - if(isFinal){ - while(candidates.length){ - matchArr.push(candidates.shift()); - } - /* - candidates.unshift(0, matchArr.length-1); - matchArr.splice.apply(matchArr, candidates); - */ - }else{ - // if we're not yet at the bottom, keep going! - while(candidates.length){ - _filterDown(candidates.shift(), queryParts, matchArr, nidx); - } - } - } - - var filterDown = function(elements, queryParts){ - var ret = []; - - // for every root, get the elements that match the descendant selector - // for(var x=elements.length-1, te; x>=0, te=elements[x]; x--){ - var x = elements.length - 1, te; - while(te = elements[x--]){ - _filterDown(te, queryParts, ret, 0); - } - return ret; - } - - var getFilterFunc = function(q){ - // note: query can't have spaces! - if(_filtersCache[q.query]){ - return _filtersCache[q.query]; - } - var ff = null; - - // does it have a tagName component? - if(q.tag){ - if(q.tag == "*"){ - ff = agree(ff, - function(elem){ - return (elem.nodeType == 1); - } - ); - }else{ - // tag name match - ff = agree(ff, - function(elem){ - return ( - (elem.nodeType == 1) && - (q.tag == elem.tagName.toLowerCase()) - ); - // return isTn; - } - ); - } - } - - // does the node have an ID? - if(q.id){ - ff = agree(ff, - function(elem){ - return ( - (elem.nodeType == 1) && - (elem.id == q.id) - ); - } - ); - } - - if(q.hasLoops){ - // if we have other query param parts, make sure we add them to the - // filter chain - ff = agree(ff, getSimpleFilterFunc(q)); - } - - return _filtersCache[q.query] = ff; - } - - var getNodeIndex = function(node){ - // NOTE: - // we could have a more accurate caching mechanism by invalidating - // caches after the query has finished, but I think that'd lead to - // significantly more cache churn than the cache would provide - // value for in the common case. Generally, we're more - // conservative (and therefore, more accurate) than jQuery and - // DomQuery WRT node node indexes, but there may be corner cases - // in which we fall down. How much we care about them is TBD. - - var pn = node.parentNode; - var pnc = pn.childNodes; - - // check to see if we can trust the cache. If not, re-key the whole - // thing and return our node match from that. - - var nidx = -1; - var child = pn.firstChild; - if(!child){ - return nidx; - } - - var ci = node["__cachedIndex"]; - var cl = pn["__cachedLength"]; - - // only handle cache building if we've gone out of sync - if(((typeof cl == "number")&&(cl != pnc.length))||(typeof ci != "number")){ - // rip though the whole set, building cache indexes as we go - pn["__cachedLength"] = pnc.length; - var idx = 1; - do{ - // we only assign indexes for nodes with nodeType == 1, as per: - // http://www.w3.org/TR/css3-selectors/#nth-child-pseudo - // only elements are counted in the search order, and they - // begin at 1 for the first child's index - - if(child === node){ - nidx = idx; - } - if(child.nodeType == 1){ - child["__cachedIndex"] = idx; - idx++; - } - child = child.nextSibling; - }while(child); - }else{ - // NOTE: - // could be incorrect in some cases (node swaps involving the - // passed node, etc.), but we ignore those due to the relative - // unlikelihood of that occuring - nidx = ci; - } - return nidx; - } - - var firedCount = 0; - - var blank = ""; - var _getAttr = function(elem, attr){ - if(attr == "class"){ - return elem.className || blank; - } - if(attr == "for"){ - return elem.htmlFor || blank; - } - return elem.getAttribute(attr, 2) || blank; - } - - var attrs = { - "*=": function(attr, value){ - return function(elem){ - // E[foo*="bar"] - // an E element whose "foo" attribute value contains - // the substring "bar" - return (_getAttr(elem, attr).indexOf(value)>=0); - } - }, - "^=": function(attr, value){ - // E[foo^="bar"] - // an E element whose "foo" attribute value begins exactly - // with the string "bar" - return function(elem){ - return (_getAttr(elem, attr).indexOf(value)==0); - } - }, - "$=": function(attr, value){ - // E[foo$="bar"] - // an E element whose "foo" attribute value ends exactly - // with the string "bar" - var tval = " "+value; - return function(elem){ - var ea = " "+_getAttr(elem, attr); - return (ea.lastIndexOf(value)==(ea.length-value.length)); - } - }, - "~=": function(attr, value){ - // E[foo~="bar"] - // an E element whose "foo" attribute value is a list of - // space-separated values, one of which is exactly equal - // to "bar" - - // return "[contains(concat(' ',@"+attr+",' '), ' "+ value +" ')]"; - var tval = " "+value+" "; - return function(elem){ - var ea = " "+_getAttr(elem, attr)+" "; - return (ea.indexOf(tval)>=0); - } - }, - "|=": function(attr, value){ - // E[hreflang|="en"] - // an E element whose "hreflang" attribute has a - // hyphen-separated list of values beginning (from the - // left) with "en" - var valueDash = " "+value+"-"; - return function(elem){ - var ea = " "+(elem.getAttribute(attr, 2) || ""); - return ( - (ea == value) || - (ea.indexOf(valueDash)==0) - ); - } - }, - "=": function(attr, value){ - return function(elem){ - return (_getAttr(elem, attr) == value); - } - } - }; - - var pseudos = { - "first-child": function(name, condition){ - return function(elem){ - if(elem.nodeType != 1){ return false; } - // check to see if any of the previous siblings are elements - var fc = elem.previousSibling; - while(fc && (fc.nodeType != 1)){ - fc = fc.previousSibling; - } - return (!fc); - } - }, - "last-child": function(name, condition){ - return function(elem){ - if(elem.nodeType != 1){ return false; } - // check to see if any of the next siblings are elements - var nc = elem.nextSibling; - while(nc && (nc.nodeType != 1)){ - nc = nc.nextSibling; - } - return (!nc); - } - }, - "empty": function(name, condition){ - return function(elem){ - // DomQuery and jQuery get this wrong, oddly enough. - // The CSS 3 selectors spec is pretty explicit about - // it, too. - var cn = elem.childNodes; - var cnl = elem.childNodes.length; - // if(!cnl){ return true; } - for(var x=cnl-1; x >= 0; x--){ - var nt = cn[x].nodeType; - if((nt == 1)||(nt == 3)){ return false; } - } - return true; - } - }, - "contains": function(name, condition){ - return function(elem){ - // FIXME: I dislike this version of "contains", as - // whimsical attribute could set it off. An inner-text - // based version might be more accurate, but since - // jQuery and DomQuery also potentially get this wrong, - // I'm leaving it for now. - return (elem.innerHTML.indexOf(condition) >= 0); - } - }, - "not": function(name, condition){ - var ntf = getFilterFunc(getQueryParts(condition)[0]); - return function(elem){ - return (!ntf(elem)); - } - }, - "nth-child": function(name, condition){ - var pi = parseInt; - if(condition == "odd"){ - return function(elem){ - return ( - ((getNodeIndex(elem)) % 2) == 1 - ); - } - }else if((condition == "2n")|| - (condition == "even")){ - return function(elem){ - return ((getNodeIndex(elem) % 2) == 0); - } - }else if(condition.indexOf("0n+") == 0){ - var ncount = pi(condition.substr(3)); - return function(elem){ - return (elem.parentNode[childNodesName][ncount-1] === elem); - } - }else if( (condition.indexOf("n+") > 0) && - (condition.length > 3) ){ - var tparts = condition.split("n+", 2); - var pred = pi(tparts[0]); - var idx = pi(tparts[1]); - return function(elem){ - return ((getNodeIndex(elem) % pred) == idx); - } - }else if(condition.indexOf("n") == -1){ - var ncount = pi(condition); - return function(elem){ - return (getNodeIndex(elem) == ncount); - } - } - } - }; - - var defaultGetter = (d.isIE) ? function(cond){ - var clc = cond.toLowerCase(); - return function(elem){ - return elem[cond]||elem[clc]; - } - } : function(cond){ - return function(elem){ - return (elem && elem.getAttribute && elem.hasAttribute(cond)); - } - }; - - var getSimpleFilterFunc = function(query){ - - var fcHit = (_simpleFiltersCache[query.query]||_filtersCache[query.query]); - if(fcHit){ return fcHit; } - - var ff = null; - - // the only case where we'll need the tag name is if we came from an ID query - if(query.id){ // do we have an ID component? - if(query.tag != "*"){ - ff = agree(ff, function(elem){ - return (elem.tagName.toLowerCase() == query.tag); - }); - } - } - - // if there's a class in our query, generate a match function for it - d.forEach(query.classes, function(cname, idx, arr){ - // get the class name - var isWildcard = cname.charAt(cname.length-1) == "*"; - if(isWildcard){ - cname = cname.substr(0, cname.length-1); - } - // I dislike the regex thing, even if memozied in a cache, but it's VERY short - var re = new RegExp("(?:^|\\s)" + cname + (isWildcard ? ".*" : "") + "(?:\\s|$)"); - ff = agree(ff, function(elem){ - return re.test(elem.className); - }); - ff.count = idx; - }); - - d.forEach(query.pseudos, function(pseudo){ - if(pseudos[pseudo.name]){ - ff = agree(ff, pseudos[pseudo.name](pseudo.name, pseudo.value)); - } - }); - - handleAttrs(attrs, query, defaultGetter, - function(tmatcher){ ff = agree(ff, tmatcher); } - ); - if(!ff){ - ff = function(){ return true; }; - } - return _simpleFiltersCache[query.query] = ff; - } - - var _getElementsFuncCache = { }; - - var getElementsFunc = function(query, root){ - var fHit = _getElementsFuncCache[query.query]; - if(fHit){ return fHit; } - - // NOTE: this function is in the fast path! not memoized!!! - - // the query doesn't contain any spaces, so there's only so many - // things it could be - - if(query.id && !query.hasLoops && !query.tag){ - // ID-only query. Easy. - return _getElementsFuncCache[query.query] = function(root){ - // FIXME: if root != document, check for parenting! - return [ d.byId(query.id) ]; - } - } - - var filterFunc = getSimpleFilterFunc(query); - - var retFunc; - if(query.tag && query.id && !query.hasLoops){ - // we got a filtered ID search (e.g., "h4#thinger") - retFunc = function(root){ - var te = d.byId(query.id); - if(filterFunc(te)){ - return [ te ]; - } - } - }else{ - var tret; - - if(!query.hasLoops){ - // it's just a plain-ol elements-by-tag-name query from the root - retFunc = function(root){ - var ret = []; - var te, x=0, tret = root.getElementsByTagName(query.tag); - while(te=tret[x++]){ - ret.push(te); - } - return ret; - } - }else{ - retFunc = function(root){ - var ret = []; - var te, x=0, tret = root.getElementsByTagName(query.tag); - while(te=tret[x++]){ - if(filterFunc(te)){ - ret.push(te); - } - } - return ret; - } - } - } - return _getElementsFuncCache[query.query] = retFunc; - } - - var _partsCache = {}; - - //////////////////////////////////////////////////////////////////////// - // the query runner - //////////////////////////////////////////////////////////////////////// - - // this is the second level of spliting, from full-length queries (e.g., - // "div.foo .bar") into simple query expressions (e.g., ["div.foo", - // ".bar"]) - var _queryFuncCache = { - "*": d.isIE ? - function(root){ - return root.all; - } : - function(root){ - return root.getElementsByTagName("*"); - }, - "~": _nextSiblings, - "+": function(root){ return _nextSiblings(root, true); }, - ">": _childElements - }; - - var getStepQueryFunc = function(query){ - // if it's trivial, get a fast-path dispatcher - var qparts = getQueryParts(d.trim(query)); - // if(query[query.length-1] == ">"){ query += " *"; } - if(qparts.length == 1){ - var tt = getElementsFunc(qparts[0]); - tt.nozip = true; - return tt; - } - - // otherwise, break it up and return a runner that iterates over the parts recursively - var sqf = function(root){ - var localQueryParts = qparts.slice(0); // clone the src arr - var candidates; - if(localQueryParts[0].oper == ">"){ // FIXME: what if it's + or ~? - candidates = [ root ]; - // root = document; - }else{ - candidates = getElementsFunc(localQueryParts.shift())(root); - } - return filterDown(candidates, localQueryParts); - } - return sqf; - } - - // a specialized method that implements our primoridal "query optimizer". - // This allows us to dispatch queries to the fastest subsystem we can get. - var _getQueryFunc = ( - // NOTE: - // XPath on the Webkit nighlies is slower than it's DOM iteration - // for most test cases - // FIXME: - // we should try to capture some runtime speed data for each query - // function to determine on the fly if we should stick w/ the - // potentially optimized variant or if we should try something - // new. - (document["evaluate"] && !d.isSafari) ? - function(query){ - // has xpath support that's faster than DOM - var qparts = query.split(" "); - // can we handle it? - if( (document["evaluate"])&& - (query.indexOf(":") == -1)&& - (query.indexOf("+") == -1) // skip direct sibling matches. See line ~344 - ){ - // dojo.debug(query); - // should we handle it? - - // kind of a lame heuristic, but it works - if( - // a "div div div" style query - ((qparts.length > 2)&&(query.indexOf(">") == -1))|| - // or something else with moderate complexity. kinda janky - (qparts.length > 3)|| - (query.indexOf("[")>=0)|| - // or if it's a ".thinger" query - ((1 == qparts.length)&&(0 <= query.indexOf("."))) - - ){ - // use get and cache a xpath runner for this selector - return getXPathFunc(query); - } - } - - // fallthrough - return getStepQueryFunc(query); - } : getStepQueryFunc - ); - // uncomment to disable XPath for testing and tuning the DOM path - // _getQueryFunc = getStepQueryFunc; - - // FIXME: we've got problems w/ the NodeList query()/filter() functions if we go XPath for everything - - // uncomment to disable DOM queries for testing and tuning XPath - // _getQueryFunc = getXPathFunc; - - // this is the primary caching for full-query results. The query dispatcher - // functions are generated here and then pickled for hash lookup in the - // future - var getQueryFunc = function(query){ - // return a cached version if one is available - var qcz = query.charAt(0); - if(d.doc["querySelectorAll"] && - ( (!d.isSafari) || (d.isSafari > 3.1) ) && // see #5832 - // as per CSS 3, we can't currently start w/ combinator: - // http://www.w3.org/TR/css3-selectors/#w3cselgrammar - (">+~".indexOf(qcz) == -1) - ){ - return function(root){ - var r = root.querySelectorAll(query); - r.nozip = true; // skip expensive duplication checks and just wrap in a NodeList - return r; - }; - } - if(_queryFuncCache[query]){ return _queryFuncCache[query]; } - if(0 > query.indexOf(",")){ - // if it's not a compound query (e.g., ".foo, .bar"), cache and return a dispatcher - return _queryFuncCache[query] = _getQueryFunc(query); - }else{ - // if it's a complex query, break it up into it's constituent parts - // and return a dispatcher that will merge the parts when run - - // var parts = query.split(", "); - var parts = query.split(/\s*,\s*/); - var tf = function(root){ - var pindex = 0; // avoid array alloc for every invocation - var ret = []; - var tp; - while(tp = parts[pindex++]){ - ret = ret.concat(_getQueryFunc(tp, tp.indexOf(" "))(root)); - } - return ret; - } - // ...cache and return - return _queryFuncCache[query] = tf; - } - } - - // FIXME: - // Dean's Base2 uses a system whereby queries themselves note if - // they'll need duplicate filtering. We need to get on that plan!! - - // attempt to efficiently determine if an item in a list is a dupe, - // returning a list of "uniques", hopefully in doucment order - var _zipIdx = 0; - var _zip = function(arr){ - if(arr && arr.nozip){ return d.NodeList._wrap(arr); } - var ret = new d.NodeList(); - if(!arr){ return ret; } - if(arr[0]){ - ret.push(arr[0]); - } - if(arr.length < 2){ return ret; } - _zipIdx++; - arr[0]["_zipIdx"] = _zipIdx; - for(var x=1, te; te = arr[x]; x++){ - if(arr[x]["_zipIdx"] != _zipIdx){ - ret.push(te); - } - te["_zipIdx"] = _zipIdx; - } - // FIXME: should we consider stripping these properties? - return ret; - } - - // the main executor - d.query = function(/*String*/ query, /*String|DOMNode?*/ root){ - // summary: - // Returns nodes which match the given CSS3 selector, searching the - // entire document by default but optionally taking a node to scope - // the search by. Returns an instance of dojo.NodeList. - // description: - // dojo.query() is the swiss army knife of DOM node manipulation in - // Dojo. Much like Prototype's "$$" (bling-bling) function or JQuery's - // "$" function, dojo.query provides robust, high-performance - // CSS-based node selector support with the option of scoping searches - // to a particular sub-tree of a document. - // - // Supported Selectors: - // -------------------- - // - // dojo.query() supports a rich set of CSS3 selectors, including: - // - // * class selectors (e.g., `.foo`) - // * node type selectors like `span` - // * ` ` descendant selectors - // * `>` child element selectors - // * `#foo` style ID selectors - // * `*` universal selector - // * `~`, the immediately preceeded-by sibling selector - // * `+`, the preceeded-by sibling selector - // * attribute queries: - // | * `[foo]` attribute presence selector - // | * `[foo='bar']` attribute value exact match - // | * `[foo~='bar']` attribute value list item match - // | * `[foo^='bar']` attribute start match - // | * `[foo$='bar']` attribute end match - // | * `[foo*='bar']` attribute substring match - // * `:first-child`, `:last-child` positional selectors - // * `:empty` content emtpy selector - // * `:empty` content emtpy selector - // * `:nth-child(n)`, `:nth-child(2n+1)` style positional calculations - // * `:nth-child(even)`, `:nth-child(odd)` positional selectors - // * `:not(...)` negation pseudo selectors - // - // Any legal combination of these selectors will work with - // `dojo.query()`, including compound selectors ("," delimited). - // Very complex and useful searches can be constructed with this - // palette of selectors and when combined with functions for - // maniplation presented by dojo.NodeList, many types of DOM - // manipulation operations become very straightforward. - // - // Unsupported Selectors: - // ---------------------- - // - // While dojo.query handles many CSS3 selectors, some fall outside of - // what's resaonable for a programmatic node querying engine to - // handle. Currently unsupported selectors include: - // - // * namespace-differentiated selectors of any form - // * all `::` pseduo-element selectors - // * certain pseduo-selectors which don't get a lot of day-to-day use: - // | * `:root`, `:lang()`, `:target`, `:focus` - // * all visual and state selectors: - // | * `:root`, `:active`, `:hover`, `:visisted`, `:link`, - // `:enabled`, `:disabled`, `:checked` - // * `:*-of-type` pseudo selectors - // - // dojo.query and XML Documents: - // ----------------------------- - // - // `dojo.query` currently only supports searching XML documents - // whose tags and attributes are 100% lower-case. This is a known - // limitation and will [be addressed soon](http://trac.dojotoolkit.org/ticket/3866) - // Non-selector Queries: - // --------------------- - // - // If something other than a String is passed for the query, - // `dojo.query` will return a new `dojo.NodeList` constructed from - // that parameter alone and all further processing will stop. This - // means that if you have a reference to a node or NodeList, you - // can quickly construct a new NodeList from the original by - // calling `dojo.query(node)` or `dojo.query(list)`. - // - // query: - // The CSS3 expression to match against. For details on the syntax of - // CSS3 selectors, see <http://www.w3.org/TR/css3-selectors/#selectors> - // root: - // A DOMNode (or node id) to scope the search from. Optional. - // returns: dojo.NodeList - // An instance of `dojo.NodeList`. Many methods are available on - // NodeLists for searching, iterating, manipulating, and handling - // events on the matched nodes in the returned list. - // example: - // search the entire document for elements with the class "foo": - // | dojo.query(".foo"); - // these elements will match: - // | <span class="foo"></span> - // | <span class="foo bar"></span> - // | <p class="thud foo"></p> - // example: - // search the entire document for elements with the classes "foo" *and* "bar": - // | dojo.query(".foo.bar"); - // these elements will match: - // | <span class="foo bar"></span> - // while these will not: - // | <span class="foo"></span> - // | <p class="thud foo"></p> - // example: - // find `<span>` elements which are descendants of paragraphs and - // which have a "highlighted" class: - // | dojo.query("p span.highlighted"); - // the innermost span in this fragment matches: - // | <p class="foo"> - // | <span>... - // | <span class="highlighted foo bar">...</span> - // | </span> - // | </p> - // example: - // set an "odd" class on all odd table rows inside of the table - // `#tabular_data`, using the `>` (direct child) selector to avoid - // affecting any nested tables: - // | dojo.query("#tabular_data > tbody > tr:nth-child(odd)").addClass("odd"); - // example: - // remove all elements with the class "error" from the document - // and store them in a list: - // | var errors = dojo.query(".error").orphan(); - // example: - // add an onclick handler to every submit button in the document - // which causes the form to be sent via Ajax instead: - // | dojo.query("input[type='submit']").onclick(function(e){ - // | dojo.stopEvent(e); // prevent sending the form - // | var btn = e.target; - // | dojo.xhrPost({ - // | form: btn.form, - // | load: function(data){ - // | // replace the form with the response - // | var div = dojo.doc.createElement("div"); - // | dojo.place(div, btn.form, "after"); - // | div.innerHTML = data; - // | dojo.style(btn.form, "display", "none"); - // | } - // | }); - // | }); - - - // NOTE: elementsById is not currently supported - // NOTE: ignores xpath-ish queries for now - - if(query.constructor == d.NodeList){ - return query; - } - if(!d.isString(query)){ - return new d.NodeList(query); // dojo.NodeList - } - if(d.isString(root)){ - root = d.byId(root); - } - - return _zip(getQueryFunc(query)(root||d.doc)); // dojo.NodeList - } - - /* - // exposing this was a mistake - d.query.attrs = attrs; - */ - // exposing this because new pseudo matches are only executed through the - // DOM query path (never through the xpath optimizing branch) - d.query.pseudos = pseudos; - - // one-off function for filtering a NodeList based on a simple selector - d._filterQueryResult = function(nodeList, simpleFilter){ - var tnl = new d.NodeList(); - var ff = (simpleFilter) ? getFilterFunc(getQueryParts(simpleFilter)[0]) : function(){ return true; }; - for(var x=0, te; te = nodeList[x]; x++){ - if(ff(te)){ tnl.push(te); } - } - return tnl; - } -})(); - -} - -if(!dojo._hasResource["dojo._base.xhr"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.xhr"] = true; -dojo.provide("dojo._base.xhr"); - - - - - -(function(){ - var _d = dojo; - function setValue(/*Object*/obj, /*String*/name, /*String*/value){ - //summary: - // For the nameed property in object, set the value. If a value - // already exists and it is a string, convert the value to be an - // array of values. - var val = obj[name]; - if(_d.isString(val)){ - obj[name] = [val, value]; - }else if(_d.isArray(val)){ - val.push(value); - }else{ - obj[name] = value; - } - } - - dojo.formToObject = function(/*DOMNode||String*/ formNode){ - // summary: - // dojo.formToObject returns the values encoded in an HTML form as - // string properties in an object which it then returns. Disabled form - // elements, buttons, and other non-value form elements are skipped. - // Multi-select elements are returned as an array of string values. - // description: - // This form: - // - // | <form id="test_form"> - // | <input type="text" name="blah" value="blah"> - // | <input type="text" name="no_value" value="blah" disabled> - // | <input type="button" name="no_value2" value="blah"> - // | <select type="select" multiple name="multi" size="5"> - // | <option value="blah">blah</option> - // | <option value="thud" selected>thud</option> - // | <option value="thonk" selected>thonk</option> - // | </select> - // | </form> - // - // yields this object structure as the result of a call to - // formToObject(): - // - // | { - // | blah: "blah", - // | multi: [ - // | "thud", - // | "thonk" - // | ] - // | }; - - var ret = {}; - var iq = "input:not([type=file]):not([type=submit]):not([type=image]):not([type=reset]):not([type=button]), select, textarea"; - _d.query(iq, formNode).filter(function(node){ - return !node.disabled && node.name; - }).forEach(function(item){ - var _in = item.name; - var type = (item.type||"").toLowerCase(); - if(type == "radio" || type == "checkbox"){ - if(item.checked){ setValue(ret, _in, item.value); } - }else if(item.multiple){ - ret[_in] = []; - _d.query("option", item).forEach(function(opt){ - if(opt.selected){ - setValue(ret, _in, opt.value); - } - }); - }else{ - setValue(ret, _in, item.value); - if(type == "image"){ - ret[_in+".x"] = ret[_in+".y"] = ret[_in].x = ret[_in].y = 0; - } - } - }); - return ret; // Object - } - - dojo.objectToQuery = function(/*Object*/ map){ - // summary: - // takes a name/value mapping object and returns a string representing - // a URL-encoded version of that object. - // example: - // this object: - // - // | { - // | blah: "blah", - // | multi: [ - // | "thud", - // | "thonk" - // | ] - // | }; - // - // yields the following query string: - // - // | "blah=blah&multi=thud&multi=thonk" - - // FIXME: need to implement encodeAscii!! - var enc = encodeURIComponent; - var pairs = []; - var backstop = {}; - for(var name in map){ - var value = map[name]; - if(value != backstop[name]){ - var assign = enc(name) + "="; - if(_d.isArray(value)){ - for(var i=0; i < value.length; i++){ - pairs.push(assign + enc(value[i])); - } - }else{ - pairs.push(assign + enc(value)); - } - } - } - return pairs.join("&"); // String - } - - dojo.formToQuery = function(/*DOMNode||String*/ formNode){ - // summary: - // Returns a URL-encoded string representing the form passed as either a - // node or string ID identifying the form to serialize - return _d.objectToQuery(_d.formToObject(formNode)); // String - } - - dojo.formToJson = function(/*DOMNode||String*/ formNode, /*Boolean?*/prettyPrint){ - // summary: - // return a serialized JSON string from a form node or string - // ID identifying the form to serialize - return _d.toJson(_d.formToObject(formNode), prettyPrint); // String - } - - dojo.queryToObject = function(/*String*/ str){ - // summary: - // returns an object representing a de-serialized query section of a - // URL. Query keys with multiple values are returned in an array. - // description: - // This string: - // - // | "foo=bar&foo=baz&thinger=%20spaces%20=blah&zonk=blarg&" - // - // results in this object structure: - // - // | { - // | foo: [ "bar", "baz" ], - // | thinger: " spaces =blah", - // | zonk: "blarg" - // | } - // - // Note that spaces and other urlencoded entities are correctly - // handled. - - // FIXME: should we grab the URL string if we're not passed one? - var ret = {}; - var qp = str.split("&"); - var dec = decodeURIComponent; - _d.forEach(qp, function(item){ - if(item.length){ - var parts = item.split("="); - var name = dec(parts.shift()); - var val = dec(parts.join("=")); - if(_d.isString(ret[name])){ - ret[name] = [ret[name]]; - } - if(_d.isArray(ret[name])){ - ret[name].push(val); - }else{ - ret[name] = val; - } - } - }); - return ret; // Object - } - - /* - from refactor.txt: - - all bind() replacement APIs take the following argument structure: - - { - url: "blah.html", - - // all below are optional, but must be supported in some form by - // every IO API - timeout: 1000, // milliseconds - handleAs: "text", // replaces the always-wrong "mimetype" - content: { - key: "value" - }, - - // browser-specific, MAY be unsupported - sync: true, // defaults to false - form: dojo.byId("someForm") - } - */ - - // need to block async callbacks from snatching this thread as the result - // of an async callback might call another sync XHR, this hangs khtml forever - // must checked by watchInFlight() - - dojo._blockAsync = false; - - dojo._contentHandlers = { - "text": function(xhr){ return xhr.responseText; }, - "json": function(xhr){ - if(!dojo.config.usePlainJson){ - console.warn("Consider using mimetype:text/json-comment-filtered" - + " to avoid potential security issues with JSON endpoints" - + " (use djConfig.usePlainJson=true to turn off this message)"); - } - return (xhr.status == 204) ? undefined : _d.fromJson(xhr.responseText); - }, - "json-comment-filtered": function(xhr){ - // NOTE: we provide the json-comment-filtered option as one solution to - // the "JavaScript Hijacking" issue noted by Fortify and others. It is - // not appropriate for all circumstances. - - var value = xhr.responseText; - var cStartIdx = value.indexOf("\/*"); - var cEndIdx = value.lastIndexOf("*\/"); - if(cStartIdx == -1 || cEndIdx == -1){ - throw new Error("JSON was not comment filtered"); - } - return (xhr.status == 204) ? undefined : - _d.fromJson(value.substring(cStartIdx+2, cEndIdx)); - }, - "javascript": function(xhr){ - // FIXME: try Moz and IE specific eval variants? - return _d.eval(xhr.responseText); - }, - "xml": function(xhr){ - var result = xhr.responseXML; - if(_d.isIE && (!result || window.location.protocol == "file:")){ - _d.forEach(["MSXML2", "Microsoft", "MSXML", "MSXML3"], function(prefix){ - try{ - var dom = new ActiveXObject(prefix + ".XMLDOM"); - dom.async = false; - dom.loadXML(xhr.responseText); - result = dom; - }catch(e){ /* Not available. Squelch and try next one. */ } - }); - } - return result; // DOMDocument - } - }; - - dojo._contentHandlers["json-comment-optional"] = function(xhr){ - var handlers = _d._contentHandlers; - try{ - return handlers["json-comment-filtered"](xhr); - }catch(e){ - return handlers["json"](xhr); - } - }; - - /*===== - dojo.__IoArgs = function(){ - // url: String - // URL to server endpoint. - // content: Object? - // Contains properties with string values. These - // properties will be serialized as name1=value2 and - // passed in the request. - // timeout: Integer? - // Milliseconds to wait for the response. If this time - // passes, the then error callbacks are called. - // form: DOMNode? - // DOM node for a form. Used to extract the form values - // and send to the server. - // preventCache: Boolean? - // Default is false. If true, then a - // "dojo.preventCache" parameter is sent in the request - // with a value that changes with each request - // (timestamp). Useful only with GET-type requests. - // handleAs: String? - // Acceptable values depend on the type of IO - // transport (see specific IO calls for more information). - // load: Function? - // function(response, ioArgs){}. response is an Object, ioArgs - // is of type dojo.__IoCallbackArgs. The load function will be - // called on a successful response. - // error: Function? - // function(response, ioArgs){}. response is an Object, ioArgs - // is of type dojo.__IoCallbackArgs. The error function will - // be called in an error case. - // handle: Function? - // function(response, ioArgs){}. response is an Object, ioArgs - // is of type dojo.__IoCallbackArgs. The handle function will - // be called in either the successful or error case. For - // the load, error and handle functions, the ioArgs object - // will contain the following properties: - this.url = url; - this.content = content; - this.timeout = timeout; - this.form = form; - this.preventCache = preventCache; - this.handleAs = handleAs; - this.load = load; - this.error = error; - this.handle = handle; - } - =====*/ - - /*===== - dojo.__IoCallbackArgs = function(args, xhr, url, query, handleAs, id, canDelete, json){ - // args: Object - // the original object argument to the IO call. - // xhr: XMLHttpRequest - // For XMLHttpRequest calls only, the - // XMLHttpRequest object that was used for the - // request. - // url: String - // The final URL used for the call. Many times it - // will be different than the original args.url - // value. - // query: String - // For non-GET requests, the - // name1=value1&name2=value2 parameters sent up in - // the request. - // handleAs: String - // The final indicator on how the response will be - // handled. - // id: String - // For dojo.io.script calls only, the internal - // script ID used for the request. - // canDelete: Boolean - // For dojo.io.script calls only, indicates - // whether the script tag that represents the - // request can be deleted after callbacks have - // been called. Used internally to know when - // cleanup can happen on JSONP-type requests. - // json: Object - // For dojo.io.script calls only: holds the JSON - // response for JSONP-type requests. Used - // internally to hold on to the JSON responses. - // You should not need to access it directly -- - // the same object should be passed to the success - // callbacks directly. - this.args = args; - this.xhr = xhr; - this.url = url; - this.query = query; - this.handleAs = handleAs; - this.id = id; - this.canDelete = canDelete; - this.json = json; - } - =====*/ - - - - dojo._ioSetArgs = function(/*dojo.__IoArgs*/args, - /*Function*/canceller, - /*Function*/okHandler, - /*Function*/errHandler){ - // summary: - // sets up the Deferred and ioArgs property on the Deferred so it - // can be used in an io call. - // args: - // The args object passed into the public io call. Recognized properties on - // the args object are: - // canceller: - // The canceller function used for the Deferred object. The function - // will receive one argument, the Deferred object that is related to the - // canceller. - // okHandler: - // The first OK callback to be registered with Deferred. It has the opportunity - // to transform the OK response. It will receive one argument -- the Deferred - // object returned from this function. - // errHandler: - // The first error callback to be registered with Deferred. It has the opportunity - // to do cleanup on an error. It will receive two arguments: error (the - // Error object) and dfd, the Deferred object returned from this function. - - var ioArgs = {args: args, url: args.url}; - - //Get values from form if requestd. - var formObject = null; - if(args.form){ - var form = _d.byId(args.form); - //IE requires going through getAttributeNode instead of just getAttribute in some form cases, - //so use it for all. See #2844 - var actnNode = form.getAttributeNode("action"); - ioArgs.url = ioArgs.url || (actnNode ? actnNode.value : null); - formObject = _d.formToObject(form); - } - - // set up the query params - var miArgs = [{}]; - - if(formObject){ - // potentially over-ride url-provided params w/ form values - miArgs.push(formObject); - } - if(args.content){ - // stuff in content over-rides what's set by form - miArgs.push(args.content); - } - if(args.preventCache){ - miArgs.push({"dojo.preventCache": new Date().valueOf()}); - } - ioArgs.query = _d.objectToQuery(_d.mixin.apply(null, miArgs)); - - // .. and the real work of getting the deferred in order, etc. - ioArgs.handleAs = args.handleAs || "text"; - var d = new _d.Deferred(canceller); - d.addCallbacks(okHandler, function(error){ - return errHandler(error, d); - }); - - //Support specifying load, error and handle callback functions from the args. - //For those callbacks, the "this" object will be the args object. - //The callbacks will get the deferred result value as the - //first argument and the ioArgs object as the second argument. - var ld = args.load; - if(ld && _d.isFunction(ld)){ - d.addCallback(function(value){ - return ld.call(args, value, ioArgs); - }); - } - var err = args.error; - if(err && _d.isFunction(err)){ - d.addErrback(function(value){ - return err.call(args, value, ioArgs); - }); - } - var handle = args.handle; - if(handle && _d.isFunction(handle)){ - d.addBoth(function(value){ - return handle.call(args, value, ioArgs); - }); - } - - d.ioArgs = ioArgs; - - // FIXME: need to wire up the xhr object's abort method to something - // analagous in the Deferred - return d; - } - - var _deferredCancel = function(/*Deferred*/dfd){ - //summary: canceller function for dojo._ioSetArgs call. - - dfd.canceled = true; - var xhr = dfd.ioArgs.xhr; - var _at = typeof xhr.abort; - if(_at == "function" || _at == "unknown"){ - xhr.abort(); - } - var err = new Error("xhr cancelled"); - err.dojoType = "cancel"; - return err; - } - var _deferredOk = function(/*Deferred*/dfd){ - //summary: okHandler function for dojo._ioSetArgs call. - - return _d._contentHandlers[dfd.ioArgs.handleAs](dfd.ioArgs.xhr); - } - var _deferError = function(/*Error*/error, /*Deferred*/dfd){ - //summary: errHandler function for dojo._ioSetArgs call. - - // console.debug("xhr error in:", dfd.ioArgs.xhr); - console.debug(error); - return error; - } - - var _makeXhrDeferred = function(/*dojo.__XhrArgs*/args){ - //summary: makes the Deferred object for this xhr request. - var dfd = _d._ioSetArgs(args, _deferredCancel, _deferredOk, _deferError); - //Pass the args to _xhrObj, to allow xhr iframe proxy interceptions. - dfd.ioArgs.xhr = _d._xhrObj(dfd.ioArgs.args); - return dfd; - } - - // avoid setting a timer per request. It degrades performance on IE - // something fierece if we don't use unified loops. - var _inFlightIntvl = null; - var _inFlight = []; - var _watchInFlight = function(){ - //summary: - // internal method that checks each inflight XMLHttpRequest to see - // if it has completed or if the timeout situation applies. - - var now = (new Date()).getTime(); - // make sure sync calls stay thread safe, if this callback is called - // during a sync call and this results in another sync call before the - // first sync call ends the browser hangs - if(!_d._blockAsync){ - // we need manual loop because we often modify _inFlight (and therefore 'i') while iterating - // note: the second clause is an assigment on purpose, lint may complain - for(var i = 0, tif; i < _inFlight.length && (tif = _inFlight[i]); i++){ - var dfd = tif.dfd; - try{ - if(!dfd || dfd.canceled || !tif.validCheck(dfd)){ - _inFlight.splice(i--, 1); - }else if(tif.ioCheck(dfd)){ - _inFlight.splice(i--, 1); - tif.resHandle(dfd); - }else if(dfd.startTime){ - //did we timeout? - if(dfd.startTime + (dfd.ioArgs.args.timeout || 0) < now){ - _inFlight.splice(i--, 1); - var err = new Error("timeout exceeded"); - err.dojoType = "timeout"; - dfd.errback(err); - //Cancel the request so the io module can do appropriate cleanup. - dfd.cancel(); - } - } - }catch(e){ - // FIXME: make sure we errback! (fixed? remove console.debug?) - console.debug(e); - dfd.errback(new Error("_watchInFlightError!")); - } - } - } - - if(!_inFlight.length){ - clearInterval(_inFlightIntvl); - _inFlightIntvl = null; - return; - } - - } - - dojo._ioCancelAll = function(){ - //summary: Cancels all pending IO requests, regardless of IO type - //(xhr, script, iframe). - try{ - _d.forEach(_inFlight, function(i){ - i.dfd.cancel(); - }); - }catch(e){/*squelch*/} - } - - //Automatically call cancel all io calls on unload - //in IE for trac issue #2357. - if(_d.isIE){ - _d.addOnUnload(_d._ioCancelAll); - } - - _d._ioWatch = function(/*Deferred*/dfd, - /*Function*/validCheck, - /*Function*/ioCheck, - /*Function*/resHandle){ - //summary: watches the io request represented by dfd to see if it completes. - //dfd: - // The Deferred object to watch. - //validCheck: - // Function used to check if the IO request is still valid. Gets the dfd - // object as its only argument. - //ioCheck: - // Function used to check if basic IO call worked. Gets the dfd - // object as its only argument. - //resHandle: - // Function used to process response. Gets the dfd - // object as its only argument. - if(dfd.ioArgs.args.timeout){ - dfd.startTime = (new Date()).getTime(); - } - _inFlight.push({dfd: dfd, validCheck: validCheck, ioCheck: ioCheck, resHandle: resHandle}); - if(!_inFlightIntvl){ - _inFlightIntvl = setInterval(_watchInFlight, 50); - } - _watchInFlight(); // handle sync requests - } - - var _defaultContentType = "application/x-www-form-urlencoded"; - - var _validCheck = function(/*Deferred*/dfd){ - return dfd.ioArgs.xhr.readyState; //boolean - } - var _ioCheck = function(/*Deferred*/dfd){ - return 4 == dfd.ioArgs.xhr.readyState; //boolean - } - var _resHandle = function(/*Deferred*/dfd){ - var xhr = dfd.ioArgs.xhr; - if(_d._isDocumentOk(xhr)){ - dfd.callback(dfd); - }else{ - var err = new Error("Unable to load " + dfd.ioArgs.url + " status:" + xhr.status); - err.status = xhr.status; - err.responseText = xhr.responseText; - dfd.errback(err); - } - } - - var _doIt = function(/*String*/type, /*Deferred*/dfd){ - // IE 6 is a steaming pile. It won't let you call apply() on the native function (xhr.open). - // workaround for IE6's apply() "issues" - var ioArgs = dfd.ioArgs; - var args = ioArgs.args; - var xhr = ioArgs.xhr; - xhr.open(type, ioArgs.url, args.sync !== true, args.user || undefined, args.password || undefined); - if(args.headers){ - for(var hdr in args.headers){ - if(hdr.toLowerCase() === "content-type" && !args.contentType){ - args.contentType = args.headers[hdr]; - }else{ - xhr.setRequestHeader(hdr, args.headers[hdr]); - } - } - } - // FIXME: is this appropriate for all content types? - xhr.setRequestHeader("Content-Type", args.contentType || _defaultContentType); - if(!args.headers || !args.headers["X-Requested-With"]){ - xhr.setRequestHeader("X-Requested-With", "XMLHttpRequest"); - } - // FIXME: set other headers here! - try{ - xhr.send(ioArgs.query); - }catch(e){ - dfd.cancel(); - } - _d._ioWatch(dfd, _validCheck, _ioCheck, _resHandle); - xhr = null; - return dfd; //Deferred - } - - dojo._ioAddQueryToUrl = function(/*dojo.__IoCallbackArgs*/ioArgs){ - //summary: Adds query params discovered by the io deferred construction to the URL. - //Only use this for operations which are fundamentally GET-type operations. - if(ioArgs.query.length){ - ioArgs.url += (ioArgs.url.indexOf("?") == -1 ? "?" : "&") + ioArgs.query; - ioArgs.query = null; - } - } - - /*===== - dojo.declare("dojo.__XhrArgs", dojo.__IoArgs, { - constructor: function(){ - // summary: - // In addition to the properties listed for the dojo._IoArgs type, - // the following properties are allowed for dojo.xhr* methods. - // handleAs: String? - // Acceptable values are: text (default), json, json-comment-optional, - // json-comment-filtered, javascript, xml - // sync: Boolean? - // false is default. Indicates whether the request should - // be a synchronous (blocking) request. - // headers: Object? - // Additional HTTP headers to send in the request. - this.handleAs = handleAs; - this.sync = sync; - this.headers = headers; - } - }); - =====*/ - - dojo.xhr = function(/*String*/ method, /*dojo.__XhrArgs*/ args, /*Boolean?*/ hasBody){ - // summary: - // Sends an HTTP request with the given method. If the request has an - // HTTP body, then pass true for hasBody. The method argument should be uppercase. - // Also look at dojo.xhrGet(), xhrPost(), xhrPut() and dojo.xhrDelete() for shortcuts - // for those HTTP methods. There are also methods for "raw" PUT and POST methods - // via dojo.rawXhrPut() and dojo.rawXhrPost() respectively. - var dfd = _makeXhrDeferred(args); - if(!hasBody){ - _d._ioAddQueryToUrl(dfd.ioArgs); - } - return _doIt(method, dfd); // dojo.Deferred - } - - dojo.xhrGet = function(/*dojo.__XhrArgs*/ args){ - // summary: - // Sends an HTTP GET request to the server. - return _d.xhr("GET", args); //dojo.Deferred - } - - dojo.xhrPost = function(/*dojo.__XhrArgs*/ args){ - //summary: - // Sends an HTTP POST request to the server. - return _d.xhr("POST", args, true); // dojo.Deferred - } - - dojo.rawXhrPost = function(/*dojo.__XhrArgs*/ args){ - // summary: - // Sends an HTTP POST request to the server. In addtion to the properties - // listed for the dojo.__XhrArgs type, the following property is allowed: - // postData: - // String. The raw data to send in the body of the POST request. - var dfd = _makeXhrDeferred(args); - dfd.ioArgs.query = args.postData; - return _doIt("POST", dfd); // dojo.Deferred - } - - dojo.xhrPut = function(/*dojo.__XhrArgs*/ args){ - // summary: - // Sends an HTTP PUT request to the server. - return _d.xhr("PUT", args, true); // dojo.Deferred - } - - dojo.rawXhrPut = function(/*dojo.__XhrArgs*/ args){ - // summary: - // Sends an HTTP PUT request to the server. In addtion to the properties - // listed for the dojo.__XhrArgs type, the following property is allowed: - // putData: - // String. The raw data to send in the body of the PUT request. - var dfd = _makeXhrDeferred(args); - var ioArgs = dfd.ioArgs; - if(args.putData){ - ioArgs.query = args.putData; - args.putData = null; - } - return _doIt("PUT", dfd); // dojo.Deferred - } - - dojo.xhrDelete = function(/*dojo.__XhrArgs*/ args){ - // summary: - // Sends an HTTP DELETE request to the server. - return _d.xhr("DELETE", args); //dojo.Deferred - } - - /* - dojo.wrapForm = function(formNode){ - //summary: - // A replacement for FormBind, but not implemented yet. - - // FIXME: need to think harder about what extensions to this we might - // want. What should we allow folks to do w/ this? What events to - // set/send? - throw new Error("dojo.wrapForm not yet implemented"); - } - */ -})(); - -} - -if(!dojo._hasResource["dojo._base.fx"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.fx"] = true; -dojo.provide("dojo._base.fx"); - - - - - - -/* - Animation losely package based on Dan Pupius' work, contributed under CLA: - http://pupius.co.uk/js/Toolkit.Drawing.js -*/ -(function(){ - - var d = dojo; - - dojo._Line = function(/*int*/ start, /*int*/ end){ - // summary: - // dojo._Line is the object used to generate values from a start value - // to an end value - // start: int - // Beginning value for range - // end: int - // Ending value for range - this.start = start; - this.end = end; - this.getValue = function(/*float*/ n){ - // summary: returns the point on the line - // n: a floating point number greater than 0 and less than 1 - return ((this.end - this.start) * n) + this.start; // Decimal - } - } - - d.declare("dojo._Animation", null, { - // summary - // A generic animation class that fires callbacks into its handlers - // object at various states. Nearly all dojo animation functions - // return an instance of this method, usually without calling the - // .play() method beforehand. Therefore, you will likely need to - // call .play() on instances of dojo._Animation when one is - // returned. - constructor: function(/*Object*/ args){ - d.mixin(this, args); - if(d.isArray(this.curve)){ - /* curve: Array - pId: a */ - this.curve = new d._Line(this.curve[0], this.curve[1]); - } - }, - - // duration: Integer - // The time in milliseonds the animation will take to run - duration: 350, - - /*===== - // curve: dojo._Line||Array - // A two element array of start and end values, or a dojo._Line instance to be - // used in the Animation. - curve: null, - - // easing: Function - // A Function to adjust the acceleration (or deceleration) of the progress - // across a dojo._Line - easing: null, - =====*/ - - // repeat: Integer - // The number of times to loop the animation - repeat: 0, - - // rate: Integer - // the time in milliseconds to wait before advancing to next frame - // (used as a fps timer: rate/1000 = fps) - rate: 10 /* 100 fps */, - - /*===== - // delay: Integer - // The time in milliseconds to wait before starting animation after it has been .play()'ed - delay: null, - - // events - // - // beforeBegin: Event - // Synthetic event fired before a dojo._Animation begins playing (synchronous) - beforeBegin: null, - - // onBegin: Event - // Synthetic event fired as a dojo._Animation begins playing (useful?) - onBegin: null, - - // onAnimate: Event - // Synthetic event fired at each interval of a dojo._Animation - onAnimate: null, - - // onEnd: Event - // Synthetic event fired after the final frame of a dojo._Animation - onEnd: null, - - // onPlay: Event - // Synthetic event fired any time a dojo._Animation is play()'ed - onPlay: null, - - // onPause: Event - // Synthetic event fired when a dojo._Animation is paused - onPause: null, - - // onStop: Event - // Synthetic event fires when a dojo._Animation is stopped - onStop: null, - - =====*/ - - _percent: 0, - _startRepeatCount: 0, - - _fire: function(/*Event*/ evt, /*Array?*/ args){ - // summary: - // Convenience function. Fire event "evt" and pass it the - // arguments specified in "args". - // evt: - // The event to fire. - // args: - // The arguments to pass to the event. - try{ - if(this[evt]){ - this[evt].apply(this, args||[]); - } - }catch(e){ - // squelch and log because we shouldn't allow exceptions in - // synthetic event handlers to cause the internal timer to run - // amuck, potentially pegging the CPU. I'm not a fan of this - // squelch, but hopefully logging will make it clear what's - // going on - console.error("exception in animation handler for:", evt); - console.error(e); - } - return this; // dojo._Animation - }, - - play: function(/*int?*/ delay, /*Boolean?*/ gotoStart){ - // summary: - // Start the animation. - // delay: - // How many milliseconds to delay before starting. - // gotoStart: - // If true, starts the animation from the beginning; otherwise, - // starts it from its current position. - var _t = this; - if(gotoStart){ - _t._stopTimer(); - _t._active = _t._paused = false; - _t._percent = 0; - }else if(_t._active && !_t._paused){ - return _t; // dojo._Animation - } - - _t._fire("beforeBegin"); - - var de = delay||_t.delay; - var _p = dojo.hitch(_t, "_play", gotoStart); - if(de > 0){ - setTimeout(_p, de); - return _t; // dojo._Animation - } - _p(); - return _t; - }, - - _play: function(gotoStart){ - var _t = this; - _t._startTime = new Date().valueOf(); - if(_t._paused){ - _t._startTime -= _t.duration * _t._percent; - } - _t._endTime = _t._startTime + _t.duration; - - _t._active = true; - _t._paused = false; - - var value = _t.curve.getValue(_t._percent); - if(!_t._percent){ - if(!_t._startRepeatCount){ - _t._startRepeatCount = _t.repeat; - } - _t._fire("onBegin", [value]); - } - - _t._fire("onPlay", [value]); - - _t._cycle(); - return _t; // dojo._Animation - }, - - pause: function(){ - // summary: Pauses a running animation. - this._stopTimer(); - if(!this._active){ return this; /*dojo._Animation*/ } - this._paused = true; - this._fire("onPause", [this.curve.getValue(this._percent)]); - return this; // dojo._Animation - }, - - gotoPercent: function(/*Decimal*/ percent, /*Boolean?*/ andPlay){ - // summary: - // Sets the progress of the animation. - // percent: - // A percentage in decimal notation (between and including 0.0 and 1.0). - // andPlay: - // If true, play the animation after setting the progress. - this._stopTimer(); - this._active = this._paused = true; - this._percent = percent; - if(andPlay){ this.play(); } - return this; // dojo._Animation - }, - - stop: function(/*boolean?*/ gotoEnd){ - // summary: Stops a running animation. - // gotoEnd: If true, the animation will end. - if(!this._timer){ return this; /* dojo._Animation */ } - this._stopTimer(); - if(gotoEnd){ - this._percent = 1; - } - this._fire("onStop", [this.curve.getValue(this._percent)]); - this._active = this._paused = false; - return this; // dojo._Animation - }, - - status: function(){ - // summary: Returns a string token representation of the status of - // the animation, one of: "paused", "playing", "stopped" - if(this._active){ - return this._paused ? "paused" : "playing"; // String - } - return "stopped"; // String - }, - - _cycle: function(){ - var _t = this; - if(_t._active){ - var curr = new Date().valueOf(); - var step = (curr - _t._startTime) / (_t._endTime - _t._startTime); - - if(step >= 1){ - step = 1; - } - _t._percent = step; - - // Perform easing - if(_t.easing){ - step = _t.easing(step); - } - - _t._fire("onAnimate", [_t.curve.getValue(step)]); - - if(_t._percent < 1){ - _t._startTimer(); - }else{ - _t._active = false; - - if(_t.repeat > 0){ - _t.repeat--; - _t.play(null, true); - }else if(_t.repeat == -1){ - _t.play(null, true); - }else{ - if(_t._startRepeatCount){ - _t.repeat = _t._startRepeatCount; - _t._startRepeatCount = 0; - } - } - _t._percent = 0; - _t._fire("onEnd"); - _t._stopTimer(); - } - } - return _t; // dojo._Animation - } - }); - - var ctr = 0; - var _globalTimerList = []; - var runner = { - run: function(){ } - }; - var timer = null; - dojo._Animation.prototype._startTimer = function(){ - // this._timer = setTimeout(dojo.hitch(this, "_cycle"), this.rate); - if(!this._timer){ - this._timer = d.connect(runner, "run", this, "_cycle"); - ctr++; - } - if(!timer){ - timer = setInterval(d.hitch(runner, "run"), this.rate); - } - }; - - dojo._Animation.prototype._stopTimer = function(){ - if(this._timer){ - d.disconnect(this._timer); - this._timer = null; - ctr--; - } - if(ctr <= 0){ - clearInterval(timer); - timer = null; - ctr = 0; - } - }; - - var _makeFadeable = (d.isIE) ? function(node){ - // only set the zoom if the "tickle" value would be the same as the - // default - var ns = node.style; - if(!ns.zoom.length && d.style(node, "zoom") == "normal"){ - // make sure the node "hasLayout" - // NOTE: this has been tested with larger and smaller user-set text - // sizes and works fine - ns.zoom = "1"; - // node.style.zoom = "normal"; - } - // don't set the width to auto if it didn't already cascade that way. - // We don't want to f anyones designs - if(!ns.width.length && d.style(node, "width") == "auto"){ - ns.width = "auto"; - } - } : function(){}; - - dojo._fade = function(/*Object*/ args){ - // summary: - // Returns an animation that will fade the node defined by - // args.node from the start to end values passed (args.start - // args.end) (end is mandatory, start is optional) - - args.node = d.byId(args.node); - var fArgs = d.mixin({ properties: {} }, args); - var props = (fArgs.properties.opacity = {}); - props.start = !("start" in fArgs) ? - function(){ - return Number(d.style(fArgs.node, "opacity")); - } : fArgs.start; - props.end = fArgs.end; - - var anim = d.animateProperty(fArgs); - d.connect(anim, "beforeBegin", d.partial(_makeFadeable, fArgs.node)); - - return anim; // dojo._Animation - } - - /*===== - dojo.__FadeArgs = function(node, duration, easing){ - // node: DOMNode|String - // The node referenced in the animation - // duration: Integer? - // Duration of the animation in milliseconds. - // easing: Function? - // An easing function. - this.node = node; - this.duration = duration; - this.easing = easing; - } - =====*/ - - dojo.fadeIn = function(/*dojo.__FadeArgs*/ args){ - // summary: - // Returns an animation that will fade node defined in 'args' from - // its current opacity to fully opaque. - return d._fade(d.mixin({ end: 1 }, args)); // dojo._Animation - } - - dojo.fadeOut = function(/*dojo.__FadeArgs*/ args){ - // summary: - // Returns an animation that will fade node defined in 'args' - // from its current opacity to fully transparent. - return d._fade(d.mixin({ end: 0 }, args)); // dojo._Animation - } - - dojo._defaultEasing = function(/*Decimal?*/ n){ - // summary: The default easing function for dojo._Animation(s) - return 0.5 + ((Math.sin((n + 1.5) * Math.PI))/2); - } - - var PropLine = function(properties){ - // PropLine is an internal class which is used to model the values of - // an a group of CSS properties across an animation lifecycle. In - // particular, the "getValue" function handles getting interpolated - // values between start and end for a particular CSS value. - this._properties = properties; - for(var p in properties){ - var prop = properties[p]; - if(prop.start instanceof d.Color){ - // create a reusable temp color object to keep intermediate results - prop.tempColor = new d.Color(); - } - } - this.getValue = function(r){ - var ret = {}; - for(var p in this._properties){ - var prop = this._properties[p]; - var start = prop.start; - if(start instanceof d.Color){ - ret[p] = d.blendColors(start, prop.end, r, prop.tempColor).toCss(); - }else if(!d.isArray(start)){ - ret[p] = ((prop.end - start) * r) + start + (p != "opacity" ? prop.units||"px" : ""); - } - } - return ret; - } - } - - /*===== - dojo.declare("dojo.__AnimArgs", [dojo.__FadeArgs], { - // Properties: Object? - // A hash map of style properties to Objects describing the transition, - // such as the properties of dojo._Line with an additional 'unit' property - properties: {} - - //TODOC: add event callbacks - }); - =====*/ - - dojo.animateProperty = function(/*dojo.__AnimArgs*/ args){ - // summary: - // Returns an animation that will transition the properties of - // node defined in 'args' depending how they are defined in - // 'args.properties' - // - // description: - // dojo.animateProperty is the foundation of most dojo.fx - // animations. It takes an object of "properties" corresponding to - // style properties, and animates them in parallel over a set - // duration. - // - // example: - // A simple animation that changes the width of the specified node. - // | dojo.animateProperty({ - // | node: "nodeId", - // | properties: { width: 400 }, - // | }).play(); - // Dojo figures out the start value for the width and converts the - // integer specified for the width to the more expressive but - // verbose form `{ width: { end: '400', units: 'px' } }` which you - // can also specify directly - // example: - // animate width, height, and padding over 2 seconds...the - // pedantic way: - // | dojo.animateProperty({ node: node, duration:2000, - // | properties: { - // | width: { start: '200', end: '400', unit:"px" }, - // | height: { start:'200', end: '400', unit:"px" }, - // | paddingTop: { start:'5', end:'50', unit:"px" } - // | } - // | }).play(); - // - // example: - // plug in a different easing function and register a callback for - // when the animation ends. Easing functions accept values between - // zero and one and return a value on that basis. In this case, an - // exponential-in curve. - // | dojo.animateProperty({ - // | node: "nodeId", - // | // dojo figures out the start value - // | properties: { width: { end: 400 } }, - // | easing: function(n){ - // | return (n==0) ? 0 : Math.pow(2, 10 * (n - 1)); - // | }, - // | onEnd: function(){ - // | // called when the animation finishes - // | } - // | }).play(500); // delay playing half a second - - args.node = d.byId(args.node); - if(!args.easing){ args.easing = d._defaultEasing; } - - var anim = new d._Animation(args); - d.connect(anim, "beforeBegin", anim, function(){ - var pm = {}; - for(var p in this.properties){ - // Make shallow copy of properties into pm because we overwrite - // some values below. In particular if start/end are functions - // we don't want to overwrite them or the functions won't be - // called if the animation is reused. - if(p == "width" || p == "height"){ - this.node.display = "block"; - } - var prop = this.properties[p]; - prop = pm[p] = d.mixin({}, (d.isObject(prop) ? prop: { end: prop })); - - if(d.isFunction(prop.start)){ - prop.start = prop.start(); - } - if(d.isFunction(prop.end)){ - prop.end = prop.end(); - } - var isColor = (p.toLowerCase().indexOf("color") >= 0); - function getStyle(node, p){ - // dojo.style(node, "height") can return "auto" or "" on IE; this is more reliable: - var v = ({height: node.offsetHeight, width: node.offsetWidth})[p]; - if(v !== undefined){ return v; } - v = d.style(node, p); - return (p=="opacity") ? Number(v) : (isColor ? v : parseFloat(v)); - } - if(!("end" in prop)){ - prop.end = getStyle(this.node, p); - }else if(!("start" in prop)){ - prop.start = getStyle(this.node, p); - } - - if(isColor){ - prop.start = new d.Color(prop.start); - prop.end = new d.Color(prop.end); - }else{ - prop.start = (p == "opacity") ? Number(prop.start) : parseFloat(prop.start); - } - } - this.curve = new PropLine(pm); - }); - d.connect(anim, "onAnimate", anim, function(propValues){ - // try{ - for(var s in propValues){ - d.style(this.node, s, propValues[s]); - // this.node.style[s] = propValues[s]; - } - }); - return anim; // dojo._Animation - } - - dojo.anim = function( /*DOMNode|String*/ node, - /*Object*/ properties, - /*Integer?*/ duration, - /*Function?*/ easing, - /*Function?*/ onEnd, - /*Integer?*/ delay){ - // summary: - // A simpler interface to `dojo.animateProperty()`, also returns - // an instance of `dojo._Animation` but begins the animation - // immediately, unlike nearly every other Dojo animation API. - // description: - // `dojo.anim` is a simpler (but somewhat less powerful) version - // of `dojo.animateProperty`. It uses defaults for many basic properties - // and allows for positional parameters to be used in place of the - // packed "property bag" which is used for other Dojo animation - // methods. - // - // The `dojo._Animation` object returned from `dojo.anim` will be - // already playing when it is returned from this function, so - // calling play() on it again is (usually) a no-op. - // node: - // a DOM node or the id of a node to animate CSS properties on - // duration: - // The number of milliseconds over which the animation - // should run. Defaults to the global animation default duration - // (350ms). - // easing: - // An easing function over which to calculate acceleration - // and deceleration of the animation through its duration. - // A default easing algorithm is provided, but you may - // plug in any you wish. A large selection of easing algorithms - // are available in `dojox.fx.easing`. - // onEnd: - // A function to be called when the animation finishes - // running. - // delay: - // The number of milliseconds to delay beginning the - // animation by. The default is 0. - // example: - // Fade out a node - // | dojo.anim("id", { opacity: 0 }); - // example: - // Fade out a node over a full second - // | dojo.anim("id", { opacity: 0 }, 1000); - return d.animateProperty({ - node: node, - duration: duration||d._Animation.prototype.duration, - properties: properties, - easing: easing, - onEnd: onEnd - }).play(delay||0); - } -})(); - -} - -if(!dojo._hasResource["dojo._base.browser"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. -dojo._hasResource["dojo._base.browser"] = true; -dojo.provide("dojo._base.browser"); - - - - - - - - - -//Need this to be the last code segment in base, so do not place any -//dojo.requireIf calls in this file. Otherwise, due to how the build system -//puts all requireIf dependencies after the current file, the require calls -//could be called before all of base is defined. -if(dojo.config.require){ - dojo.forEach(dojo.config.require, "dojo['require'](item);"); -} - -} - - - if(dojo.config.afterOnLoad && dojo.isBrowser){ - //Dojo is being added to the page after page load, so just trigger - //the init sequence after a timeout. Using a timeout so the rest of this - //script gets evaluated properly. This work needs to happen after the - //dojo.config.require work done in dojo._base. - window.setTimeout(dojo._fakeLoadInit, 1000); - } - -})(); - Copied: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js (from rev 1396, branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js) =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,9437 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + +/* + This is a compiled version of Dojo, built for deployment and not for + development. To get an editable version, please visit: + + http://dojotoolkit.org + + for documentation and information on getting the source. +*/ + +;(function(){ + + /* + dojo, dijit, and dojox must always be the first three, and in that order. + djConfig.scopeMap = [ + ["dojo", "fojo"], + ["dijit", "fijit"], + ["dojox", "fojox"] + + ] + */ + + /**Build will replace this comment with a scoped djConfig **/ + + //The null below can be relaced by a build-time value used instead of djConfig.scopeMap. + var sMap = null; + + //See if new scopes need to be defined. + if((sMap || (typeof djConfig != "undefined" && djConfig.scopeMap)) && (typeof window != "undefined")){ + var scopeDef = "", scopePrefix = "", scopeSuffix = "", scopeMap = {}, scopeMapRev = {}; + sMap = sMap || djConfig.scopeMap; + for(var i = 0; i < sMap.length; i++){ + //Make local variables, then global variables that use the locals. + var newScope = sMap[i]; + scopeDef += "var " + newScope[0] + " = {}; " + newScope[1] + " = " + newScope[0] + ";" + newScope[1] + "._scopeName = '" + newScope[1] + "';"; + scopePrefix += (i == 0 ? "" : ",") + newScope[0]; + scopeSuffix += (i == 0 ? "" : ",") + newScope[1]; + scopeMap[newScope[0]] = newScope[1]; + scopeMapRev[newScope[1]] = newScope[0]; + } + + eval(scopeDef + "dojo._scopeArgs = [" + scopeSuffix + "];"); + + dojo._scopePrefixArgs = scopePrefix; + dojo._scopePrefix = "(function(" + scopePrefix + "){"; + dojo._scopeSuffix = "})(" + scopeSuffix + ")"; + dojo._scopeMap = scopeMap; + dojo._scopeMapRev = scopeMapRev; + } + +/*===== +// note: +// 'djConfig' does not exist under 'dojo.*' so that it can be set before the +// 'dojo' variable exists. +// note: +// Setting any of these variables *after* the library has loaded does +// nothing at all. + +djConfig = { + // summary: + // Application code can set the global 'djConfig' prior to loading + // the library to override certain global settings for how dojo works. + // + // isDebug: Boolean + // Defaults to `false`. If set to `true`, ensures that Dojo provides + // extended debugging feedback via Firebug. If Firebug is not available + // on your platform, setting `isDebug` to `true` will force Dojo to + // pull in (and display) the version of Firebug Lite which is + // integrated into the Dojo distribution, thereby always providing a + // debugging/logging console when `isDebug` is enabled. Note that + // Firebug's `console.*` methods are ALWAYS defined by Dojo. If + // `isDebug` is false and you are on a platform without Firebug, these + // methods will be defined as no-ops. + isDebug: false, + // debugAtAllCosts: Boolean + // Defaults to `false`. If set to `true`, this triggers an alternate + // mode of the package system in which dependencies are detected and + // only then are resources evaluated in dependency order via + // `<script>` tag inclusion. This may double-request resources and + // cause problems with scripts which expect `dojo.require()` to + // preform synchronously. `debugAtAllCosts` can be an invaluable + // debugging aid, but when using it, ensure that all code which + // depends on Dojo modules is wrapped in `dojo.addOnLoad()` handlers. + // Due to the somewhat unpredictable side-effects of using + // `debugAtAllCosts`, it is strongly recommended that you enable this + // flag as a last resort. `debugAtAllCosts` has no effect when loading + // resources across domains. For usage information, see the + // [Dojo Book](http://dojotoolkit.org/book/book-dojo/part-4-meta-dojo-making-your-dojo-code-run-faster-and-better/debugging-facilities/deb) + debugAtAllCosts: false, + // locale: String + // The locale to assume for loading localized resources in this page, + // specified according to [RFC 3066](http://www.ietf.org/rfc/rfc3066.txt). + // Must be specified entirely in lowercase, e.g. `en-us` and `zh-cn`. + // See the documentation for `dojo.i18n` and `dojo.requireLocalization` + // for details on loading localized resources. If no locale is specified, + // Dojo assumes the locale of the user agent, according to `navigator.userLanguage` + // or `navigator.language` properties. + locale: undefined, + // extraLocale: Array + // No default value. Specifies additional locales whose + // resources should also be loaded alongside the default locale when + // calls to `dojo.requireLocalization()` are processed. + extraLocale: undefined, + // baseUrl: String + // The directory in which `dojo.js` is located. Under normal + // conditions, Dojo auto-detects the correct location from which it + // was loaded. You may need to manually configure `baseUrl` in cases + // where you have renamed `dojo.js` or in which `<base>` tags confuse + // some browsers (e.g. IE 6). The variable `dojo.baseUrl` is assigned + // either the value of `djConfig.baseUrl` if one is provided or the + // auto-detected root if not. Other modules are located relative to + // this path. The path should end in a slash. + baseUrl: undefined, + // modulePaths: Object + // A map of module names to paths relative to `dojo.baseUrl`. The + // key/value pairs correspond directly to the arguments which + // `dojo.registerModulePath` accepts. Specifiying + // `djConfig.modulePaths = { "foo": "../../bar" }` is the equivalent + // of calling `dojo.registerModulePath("foo", "../../bar");`. Multiple + // modules may be configured via `djConfig.modulePaths`. + modulePaths: {}, + // afterOnLoad: Boolean + // Indicates Dojo was added to the page after the page load. In this case + // Dojo will not wait for the page DOMContentLoad/load events and fire + // its dojo.addOnLoad callbacks after making sure all outstanding + // dojo.required modules have loaded. + afterOnLoad: false, + // addOnLoad: Function or Array + // Adds a callback via dojo.addOnLoad. Useful when Dojo is added after + // the page loads and djConfig.afterOnLoad is true. Supports the same + // arguments as dojo.addOnLoad. When using a function reference, use + // `djConfig.addOnLoad = function(){};`. For object with function name use + // `djConfig.addOnLoad = [myObject, "functionName"];` and for object with + // function reference use + // `djConfig.addOnLoad = [myObject, function(){}];` + addOnLoad: null, + // require: Array + // An array of module names to be loaded immediately after dojo.js has been included + // in a page. + require: [], + // defaultDuration: Array + // Default duration, in milliseconds, for wipe and fade animations within dijits. + // Assigned to dijit.defaultDuration. + defaultDuration: 200, + // dojoBlankHtmlUrl: String + // Used by some modules to configure an empty iframe. Used by dojo.io.iframe and + // dojo.back, and dijit popup support in IE where an iframe is needed to make sure native + // controls do not bleed through the popups. Normally this configuration variable + // does not need to be set, except when using cross-domain/CDN Dojo builds. + // Save dojo/resources/blank.html to your domain and set `djConfig.dojoBlankHtmlUrl` + // to the path on your domain your copy of blank.html. + dojoBlankHtmlUrl: undefined +} +=====*/ + +(function(){ + // firebug stubs + + if(typeof this["loadFirebugConsole"] == "function"){ + // for Firebug 1.2 + this["loadFirebugConsole"](); + }else{ + this.console = this.console || {}; + + // Be careful to leave 'log' always at the end + var cn = [ + "assert", "count", "debug", "dir", "dirxml", "error", "group", + "groupEnd", "info", "profile", "profileEnd", "time", "timeEnd", + "trace", "warn", "log" + ]; + var i=0, tn; + while((tn=cn[i++])){ + if(!console[tn]){ + (function(){ + var tcn = tn+""; + console[tcn] = ('log' in console) ? function(){ + var a = Array.apply({}, arguments); + a.unshift(tcn+":"); + console["log"](a.join(" ")); + } : function(){} + })(); + } + } + } + + //TODOC: HOW TO DOC THIS? + // dojo is the root variable of (almost all) our public symbols -- make sure it is defined. + if(typeof dojo == "undefined"){ + this.dojo = { + _scopeName: "dojo", + _scopePrefix: "", + _scopePrefixArgs: "", + _scopeSuffix: "", + _scopeMap: {}, + _scopeMapRev: {} + }; + } + + var d = dojo; + + //Need placeholders for dijit and dojox for scoping code. + if(typeof dijit == "undefined"){ + this.dijit = {_scopeName: "dijit"}; + } + if(typeof dojox == "undefined"){ + this.dojox = {_scopeName: "dojox"}; + } + + if(!d._scopeArgs){ + d._scopeArgs = [dojo, dijit, dojox]; + } + +/*===== +dojo.global = { + // summary: + // Alias for the global scope + // (e.g. the window object in a browser). + // description: + // Refer to 'dojo.global' rather than referring to window to ensure your + // code runs correctly in contexts other than web browsers (e.g. Rhino on a server). +} +=====*/ + d.global = this; + + d.config =/*===== djConfig = =====*/{ + isDebug: false, + debugAtAllCosts: false + }; + + if(typeof djConfig != "undefined"){ + for(var opt in djConfig){ + d.config[opt] = djConfig[opt]; + } + } + +/*===== + // Override locale setting, if specified + dojo.locale = { + // summary: the locale as defined by Dojo (read-only) + }; +=====*/ + dojo.locale = d.config.locale; + + var rev = "$Rev: 17468 $".match(/\d+/); + + dojo.version = { + // summary: + // version number of dojo + // major: Integer + // Major version. If total version is "1.2.0beta1", will be 1 + // minor: Integer + // Minor version. If total version is "1.2.0beta1", will be 2 + // patch: Integer + // Patch version. If total version is "1.2.0beta1", will be 0 + // flag: String + // Descriptor flag. If total version is "1.2.0beta1", will be "beta1" + // revision: Number + // The SVN rev from which dojo was pulled + major: 1, minor: 3, patch: 1, flag: "", + revision: rev ? +rev[0] : NaN, + toString: function(){ + with(d.version){ + return major + "." + minor + "." + patch + flag + " (" + revision + ")"; // String + } + } + } + + // Register with the OpenAjax hub + if(typeof OpenAjax != "undefined"){ + OpenAjax.hub.registerLibrary(dojo._scopeName, "http://dojotoolkit.org", d.version.toString()); + } + + var tobj = {}; + dojo._mixin = function(/*Object*/ obj, /*Object*/ props){ + // summary: + // Adds all properties and methods of props to obj. This addition + // is "prototype extension safe", so that instances of objects + // will not pass along prototype defaults. + for(var x in props){ + // the "tobj" condition avoid copying properties in "props" + // inherited from Object.prototype. For example, if obj has a custom + // toString() method, don't overwrite it with the toString() method + // that props inherited from Object.prototype + if(tobj[x] === undefined || tobj[x] != props[x]){ + obj[x] = props[x]; + } + } + // IE doesn't recognize custom toStrings in for..in + if(d.isIE && props){ + var p = props.toString; + if(typeof p == "function" && p != obj.toString && p != tobj.toString && + p != "\nfunction toString() {\n [native code]\n}\n"){ + obj.toString = props.toString; + } + } + return obj; // Object + } + + dojo.mixin = function(/*Object*/obj, /*Object...*/props){ + // summary: + // Adds all properties and methods of props to obj and returns the + // (now modified) obj. + // description: + // `dojo.mixin` can mix multiple source objects into a + // destionation object which is then returned. Unlike regular + // `for...in` iteration, `dojo.mixin` is also smart about avoiding + // extensions which other toolkits may unwisely add to the root + // object prototype + // obj: + // The object to mix properties into. Also the return value. + // props: + // One or more objects whose values are successively copied into + // obj. If more than one of these objects contain the same value, + // the one specified last in the function call will "win". + // example: + // make a shallow copy of an object + // | var copy = dojo.mixin({}, source); + // example: + // many class constructors often take an object which specifies + // values to be configured on the object. In this case, it is + // often simplest to call `dojo.mixin` on the `this` object: + // | dojo.declare("acme.Base", null, { + // | constructor: function(properties){ + // | // property configuration: + // | dojo.mixin(this, properties); + // | + // | + // | // ... + // | }, + // | quip: "I wasn't born yesterday, you know - I've seen movies.", + // | // ... + // | }); + // | + // | // create an instance of the class and configure it + // | var b = new acme.Base({quip: "That's what it does!" }); + // example: + // copy in properties from multiple objects + // | var flattened = dojo.mixin( + // | { + // | name: "Frylock", + // | braces: true + // | }, + // | { + // | name: "Carl Brutanananadilewski" + // | } + // | ); + // | + // | // will print "Carl Brutanananadilewski" + // | + // | // will print "true" + // | + if(!obj){ obj = {}; } + for(var i=1, l=arguments.length; i<l; i++){ + d._mixin(obj, arguments[i]); + } + return obj; // Object + } + + dojo._getProp = function(/*Array*/parts, /*Boolean*/create, /*Object*/context){ + var obj=context || d.global; + for(var i=0, p; obj && (p=parts[i]); i++){ + if(i == 0 && this._scopeMap[p]){ + p = this._scopeMap[p]; + } + obj = (p in obj ? obj[p] : (create ? obj[p]={} : undefined)); + } + return obj; // mixed + } + + dojo.setObject = function(/*String*/name, /*Object*/value, /*Object?*/context){ + // summary: + // Set a property from a dot-separated string, such as "A.B.C" + // description: + // Useful for longer api chains where you have to test each object in + // the chain, or when you have an object reference in string format. + // Objects are created as needed along `path`. Returns the passed + // value if setting is successful or `undefined` if not. + // name: + // Path to a property, in the form "A.B.C". + // context: + // Optional. Object to use as root of path. Defaults to + // `dojo.global`. + // example: + // set the value of `foo.bar.baz`, regardless of whether + // intermediate objects already exist: + // | dojo.setObject("foo.bar.baz", value); + // example: + // without `dojo.setObject`, we often see code like this: + // | // ensure that intermediate objects are available + // | if(!obj["parent"]){ obj.parent = {}; } + // | if(!obj.parent["child"]){ obj.parent.child= {}; } + // | // now we can safely set the property + // | obj.parent.child.prop = "some value"; + // wheras with `dojo.setObject`, we can shorten that to: + // | dojo.setObject("parent.child.prop", "some value", obj); + var parts=name.split("."), p=parts.pop(), obj=d._getProp(parts, true, context); + return obj && p ? (obj[p]=value) : undefined; // Object + } + + dojo.getObject = function(/*String*/name, /*Boolean?*/create, /*Object?*/context){ + // summary: + // Get a property from a dot-separated string, such as "A.B.C" + // description: + // Useful for longer api chains where you have to test each object in + // the chain, or when you have an object reference in string format. + // name: + // Path to an property, in the form "A.B.C". + // create: + // Optional. Defaults to `false`. If `true`, Objects will be + // created at any point along the 'path' that is undefined. + // context: + // Optional. Object to use as root of path. Defaults to + // 'dojo.global'. Null may be passed. + return d._getProp(name.split("."), create, context); // Object + } + + dojo.exists = function(/*String*/name, /*Object?*/obj){ + // summary: + // determine if an object supports a given method + // description: + // useful for longer api chains where you have to test each object in + // the chain + // name: + // Path to an object, in the form "A.B.C". + // obj: + // Object to use as root of path. Defaults to + // 'dojo.global'. Null may be passed. + // example: + // | // define an object + // | var foo = { + // | bar: { } + // | }; + // | + // | // search the global scope + // | dojo.exists("foo.bar"); // true + // | dojo.exists("foo.bar.baz"); // false + // | + // | // search from a particular scope + // | dojo.exists("bar", foo); // true + // | dojo.exists("bar.baz", foo); // false + return !!d.getObject(name, false, obj); // Boolean + } + + + dojo["eval"] = function(/*String*/ scriptFragment){ + // summary: + // Perform an evaluation in the global scope. Use this rather than + // calling 'eval()' directly. + // description: + // Placed in a separate function to minimize size of trapped + // exceptions. Calling eval() directly from some other scope may + // complicate tracebacks on some platforms. + // returns: + // The result of the evaluation. Often `undefined` + + + // note: + // - JSC eval() takes an optional second argument which can be 'unsafe'. + // - Mozilla/SpiderMonkey eval() takes an optional second argument which is the + // scope object for new symbols. + + // FIXME: investigate Joseph Smarr's technique for IE: + // http://josephsmarr.com/2007/01/31/fixing-eval-to-use-global-scope-in-ie/ + // see also: + // http://trac.dojotoolkit.org/ticket/744 + return d.global.eval ? d.global.eval(scriptFragment) : eval(scriptFragment); // Object + } + + /*===== + dojo.deprecated = function(behaviour, extra, removal){ + // summary: + // Log a debug message to indicate that a behavior has been + // deprecated. + // behaviour: String + // The API or behavior being deprecated. Usually in the form + // of "myApp.someFunction()". + // extra: String? + // Text to append to the message. Often provides advice on a + // new function or facility to achieve the same goal during + // the deprecation period. + // removal: String? + // Text to indicate when in the future the behavior will be + // removed. Usually a version number. + // example: + // | dojo.deprecated("myApp.getTemp()", "use myApp.getLocaleTemp() instead", "1.0"); + } + + dojo.experimental = function(moduleName, extra){ + // summary: Marks code as experimental. + // description: + // This can be used to mark a function, file, or module as + // experimental. Experimental code is not ready to be used, and the + // APIs are subject to change without notice. Experimental code may be + // completed deleted without going through the normal deprecation + // process. + // moduleName: String + // The name of a module, or the name of a module file or a specific + // function + // extra: String? + // some additional message for the user + // example: + // | dojo.experimental("dojo.data.Result"); + // example: + // | dojo.experimental("dojo.weather.toKelvin()", "PENDING approval from NOAA"); + } + =====*/ + + //Real functions declared in dojo._firebug.firebug. + d.deprecated = d.experimental = function(){}; + +})(); +// vim:ai:ts=4:noet + +/* + * loader.js - A bootstrap module. Runs before the hostenv_*.js file. Contains + * all of the package loading methods. + */ + +(function(){ + var d = dojo; + + d.mixin(d, { + _loadedModules: {}, + _inFlightCount: 0, + _hasResource: {}, + + _modulePrefixes: { + dojo: { name: "dojo", value: "." }, + // dojox: { name: "dojox", value: "../dojox" }, + // dijit: { name: "dijit", value: "../dijit" }, + doh: { name: "doh", value: "../util/doh" }, + tests: { name: "tests", value: "tests" } + }, + + _moduleHasPrefix: function(/*String*/module){ + // summary: checks to see if module has been established + var mp = this._modulePrefixes; + return !!(mp[module] && mp[module].value); // Boolean + }, + + _getModulePrefix: function(/*String*/module){ + // summary: gets the prefix associated with module + var mp = this._modulePrefixes; + if(this._moduleHasPrefix(module)){ + return mp[module].value; // String + } + return module; // String + }, + + _loadedUrls: [], + + //WARNING: + // This variable is referenced by packages outside of bootstrap: + // FloatingPane.js and undo/browser.js + _postLoad: false, + + //Egad! Lots of test files push on this directly instead of using dojo.addOnLoad. + _loaders: [], + _unloaders: [], + _loadNotifying: false + }); + + + dojo._loadPath = function(/*String*/relpath, /*String?*/module, /*Function?*/cb){ + // summary: + // Load a Javascript module given a relative path + // + // description: + // Loads and interprets the script located at relpath, which is + // relative to the script root directory. If the script is found but + // its interpretation causes a runtime exception, that exception is + // not caught by us, so the caller will see it. We return a true + // value if and only if the script is found. + // + // relpath: + // A relative path to a script (no leading '/', and typically ending + // in '.js'). + // module: + // A module whose existance to check for after loading a path. Can be + // used to determine success or failure of the load. + // cb: + // a callback function to pass the result of evaluating the script + + var uri = ((relpath.charAt(0) == '/' || relpath.match(/^\w+:/)) ? "" : this.baseUrl) + relpath; + try{ + return !module ? this._loadUri(uri, cb) : this._loadUriAndCheck(uri, module, cb); // Boolean + }catch(e){ + console.error(e); + return false; // Boolean + } + } + + dojo._loadUri = function(/*String*/uri, /*Function?*/cb){ + // summary: + // Loads JavaScript from a URI + // description: + // Reads the contents of the URI, and evaluates the contents. This is + // used to load modules as well as resource bundles. Returns true if + // it succeeded. Returns false if the URI reading failed. Throws if + // the evaluation throws. + // uri: a uri which points at the script to be loaded + // cb: + // a callback function to process the result of evaluating the script + // as an expression, typically used by the resource bundle loader to + // load JSON-style resources + + if(this._loadedUrls[uri]){ + return true; // Boolean + } + var contents = this._getText(uri, true); + if(!contents){ return false; } // Boolean + this._loadedUrls[uri] = true; + this._loadedUrls.push(uri); + if(cb){ + contents = '('+contents+')'; + }else{ + //Only do the scoping if no callback. If a callback is specified, + //it is most likely the i18n bundle stuff. + contents = this._scopePrefix + contents + this._scopeSuffix; + } + if(d.isMoz){ contents += "\r\n//@ sourceURL=" + uri; } // debugging assist for Firebug + var value = d["eval"](contents); + if(cb){ cb(value); } + return true; // Boolean + } + + // FIXME: probably need to add logging to this method + dojo._loadUriAndCheck = function(/*String*/uri, /*String*/moduleName, /*Function?*/cb){ + // summary: calls loadUri then findModule and returns true if both succeed + var ok = false; + try{ + ok = this._loadUri(uri, cb); + }catch(e){ + console.error("failed loading " + uri + " with error: " + e); + } + return !!(ok && this._loadedModules[moduleName]); // Boolean + } + + dojo.loaded = function(){ + // summary: + // signal fired when initial environment and package loading is + // complete. You should use dojo.addOnLoad() instead of doing a + // direct dojo.connect() to this method in order to handle + // initialization tasks that require the environment to be + // initialized. In a browser host, declarative widgets will + // be constructed when this function finishes runing. + this._loadNotifying = true; + this._postLoad = true; + var mll = d._loaders; + + //Clear listeners so new ones can be added + //For other xdomain package loads after the initial load. + this._loaders = []; + + for(var x = 0; x < mll.length; x++){ + mll[x](); + } + + this._loadNotifying = false; + + //Make sure nothing else got added to the onload queue + //after this first run. If something did, and we are not waiting for any + //more inflight resources, run again. + if(d._postLoad && d._inFlightCount == 0 && mll.length){ + d._callLoaded(); + } + } + + dojo.unloaded = function(){ + // summary: + // signal fired by impending environment destruction. You should use + // dojo.addOnUnload() instead of doing a direct dojo.connect() to this + // method to perform page/application cleanup methods. See + // dojo.addOnUnload for more info. + var mll = d._unloaders; + while(mll.length){ + (mll.pop())(); + } + } + + d._onto = function(arr, obj, fn){ + if(!fn){ + arr.push(obj); + }else if(fn){ + var func = (typeof fn == "string") ? obj[fn] : fn; + arr.push(function(){ func.call(obj); }); + } + } + + dojo.addOnLoad = function(/*Object?*/obj, /*String|Function*/functionName){ + // summary: + // Registers a function to be triggered after the DOM has finished + // loading and widgets declared in markup have been instantiated. + // Images and CSS files may or may not have finished downloading when + // the specified function is called. (Note that widgets' CSS and HTML + // code is guaranteed to be downloaded before said widgets are + // instantiated.) + // example: + // | dojo.addOnLoad(functionPointer); + // | dojo.addOnLoad(object, "functionName"); + // | dojo.addOnLoad(object, function(){ /* ... */}); + + d._onto(d._loaders, obj, functionName); + + //Added for xdomain loading. dojo.addOnLoad is used to + //indicate callbacks after doing some dojo.require() statements. + //In the xdomain case, if all the requires are loaded (after initial + //page load), then immediately call any listeners. + if(d._postLoad && d._inFlightCount == 0 && !d._loadNotifying){ + d._callLoaded(); + } + } + + //Support calling dojo.addOnLoad via djConfig.addOnLoad. Support all the + //call permutations of dojo.addOnLoad. Mainly useful when dojo is added + //to the page after the page has loaded. + var dca = d.config.addOnLoad; + if(dca){ + d.addOnLoad[(dca instanceof Array ? "apply" : "call")](d, dca); + } + + dojo._modulesLoaded = function(){ + if(d._postLoad){ return; } + if(d._inFlightCount > 0){ + console.warn("files still in flight!"); + return; + } + d._callLoaded(); + } + + dojo._callLoaded = function(){ + + // The "object" check is for IE, and the other opera check fixes an + // issue in Opera where it could not find the body element in some + // widget test cases. For 0.9, maybe route all browsers through the + // setTimeout (need protection still for non-browser environments + // though). This might also help the issue with FF 2.0 and freezing + // issues where we try to do sync xhr while background css images are + // being loaded (trac #2572)? Consider for 0.9. + if(typeof setTimeout == "object" || (dojo.config.useXDomain && d.isOpera)){ + if(dojo.isAIR){ + setTimeout(function(){dojo.loaded();}, 0); + }else{ + setTimeout(dojo._scopeName + ".loaded();", 0); + } + }else{ + d.loaded(); + } + } + + dojo._getModuleSymbols = function(/*String*/modulename){ + // summary: + // Converts a module name in dotted JS notation to an array + // representing the path in the source tree + var syms = modulename.split("."); + for(var i = syms.length; i>0; i--){ + var parentModule = syms.slice(0, i).join("."); + if((i==1) && !this._moduleHasPrefix(parentModule)){ + // Support default module directory (sibling of dojo) for top-level modules + syms[0] = "../" + syms[0]; + }else{ + var parentModulePath = this._getModulePrefix(parentModule); + if(parentModulePath != parentModule){ + syms.splice(0, i, parentModulePath); + break; + } + } + } + return syms; // Array + } + + dojo._global_omit_module_check = false; + + dojo.loadInit = function(/*Function*/init){ + // summary: + // Executes a function that needs to be executed for the loader's dojo.requireIf + // resolutions to work. This is needed mostly for the xdomain loader case where + // a function needs to be executed to set up the possible values for a dojo.requireIf + // call. + // init: + // a function reference. Executed immediately. + // description: This function is mainly a marker for the xdomain loader to know parts of + // code that needs be executed outside the function wrappper that is placed around modules. + // The init function could be executed more than once, and it should make no assumptions + // on what is loaded, or what modules are available. Only the functionality in Dojo Base + // is allowed to be used. Avoid using this method. For a valid use case, + // see the source for dojox.gfx. + init(); + } + + dojo._loadModule = dojo.require = function(/*String*/moduleName, /*Boolean?*/omitModuleCheck){ + // summary: + // loads a Javascript module from the appropriate URI + // moduleName: + // module name to load, using periods for separators, + // e.g. "dojo.date.locale". Module paths are de-referenced by dojo's + // internal mapping of locations to names and are disambiguated by + // longest prefix. See `dojo.registerModulePath()` for details on + // registering new modules. + // omitModuleCheck: + // if `true`, omitModuleCheck skips the step of ensuring that the + // loaded file actually defines the symbol it is referenced by. + // For example if it called as `dojo.require("a.b.c")` and the + // file located at `a/b/c.js` does not define an object `a.b.c`, + // and exception will be throws whereas no exception is raised + // when called as `dojo.require("a.b.c", true)` + // description: + // `dojo.require("A.B")` first checks to see if symbol A.B is + // defined. If it is, it is simply returned (nothing to do). + // + // If it is not defined, it will look for `A/B.js` in the script root + // directory. + // + // `dojo.require` throws an excpetion if it cannot find a file + // to load, or if the symbol `A.B` is not defined after loading. + // + // It returns the object `A.B`. + // + // `dojo.require()` does nothing about importing symbols into + // the current namespace. It is presumed that the caller will + // take care of that. For example, to import all symbols into a + // local block, you might write: + // + // | with (dojo.require("A.B")) { + // | ... + // | } + // + // And to import just the leaf symbol to a local variable: + // + // | var B = dojo.require("A.B"); + // | ... + // returns: the required namespace object + omitModuleCheck = this._global_omit_module_check || omitModuleCheck; + + //Check if it is already loaded. + var module = this._loadedModules[moduleName]; + if(module){ + return module; + } + + // convert periods to slashes + var relpath = this._getModuleSymbols(moduleName).join("/") + '.js'; + + var modArg = (!omitModuleCheck) ? moduleName : null; + var ok = this._loadPath(relpath, modArg); + + if(!ok && !omitModuleCheck){ + throw new Error("Could not load '" + moduleName + "'; last tried '" + relpath + "'"); + } + + // check that the symbol was defined + // Don't bother if we're doing xdomain (asynchronous) loading. + if(!omitModuleCheck && !this._isXDomain){ + // pass in false so we can give better error + module = this._loadedModules[moduleName]; + if(!module){ + throw new Error("symbol '" + moduleName + "' is not defined after loading '" + relpath + "'"); + } + } + + return module; + } + + dojo.provide = function(/*String*/ resourceName){ + // summary: + // Each javascript source file must have at least one + // `dojo.provide()` call at the top of the file, corresponding to + // the file name. For example, `js/dojo/foo.js` must have + // `dojo.provide("dojo.foo");` before any calls to + // `dojo.require()` are made. + // description: + // Each javascript source file is called a resource. When a + // resource is loaded by the browser, `dojo.provide()` registers + // that it has been loaded. + // + // For backwards compatibility reasons, in addition to registering + // the resource, `dojo.provide()` also ensures that the javascript + // object for the module exists. For example, + // `dojo.provide("dojox.data.FlickrStore")`, in addition to + // registering that `FlickrStore.js` is a resource for the + // `dojox.data` module, will ensure that the `dojox.data` + // javascript object exists, so that calls like + // `dojo.data.foo = function(){ ... }` don't fail. + // + // In the case of a build where multiple javascript source files + // are combined into one bigger file (similar to a .lib or .jar + // file), that file may contain multiple dojo.provide() calls, to + // note that it includes multiple resources. + + //Make sure we have a string. + resourceName = resourceName + ""; + return (d._loadedModules[resourceName] = d.getObject(resourceName, true)); // Object + } + + //Start of old bootstrap2: + + dojo.platformRequire = function(/*Object*/modMap){ + // summary: + // require one or more modules based on which host environment + // Dojo is currently operating in + // description: + // This method takes a "map" of arrays which one can use to + // optionally load dojo modules. The map is indexed by the + // possible dojo.name_ values, with two additional values: + // "default" and "common". The items in the "default" array will + // be loaded if none of the other items have been choosen based on + // dojo.name_, set by your host environment. The items in the + // "common" array will *always* be loaded, regardless of which + // list is chosen. + // example: + // | dojo.platformRequire({ + // | browser: [ + // | "foo.sample", // simple module + // | "foo.test", + // | ["foo.bar.baz", true] // skip object check in _loadModule (dojo.require) + // | ], + // | default: [ "foo.sample._base" ], + // | common: [ "important.module.common" ] + // | }); + + var common = modMap.common || []; + var result = common.concat(modMap[d._name] || modMap["default"] || []); + + for(var x=0; x<result.length; x++){ + var curr = result[x]; + if(curr.constructor == Array){ + d._loadModule.apply(d, curr); + }else{ + d._loadModule(curr); + } + } + } + + dojo.requireIf = function(/*Boolean*/ condition, /*String*/ resourceName){ + // summary: + // If the condition is true then call dojo.require() for the specified + // resource + if(condition === true){ + // FIXME: why do we support chained require()'s here? does the build system? + var args = []; + for(var i = 1; i < arguments.length; i++){ + args.push(arguments[i]); + } + d.require.apply(d, args); + } + } + + dojo.requireAfterIf = d.requireIf; + + dojo.registerModulePath = function(/*String*/module, /*String*/prefix){ + // summary: + // maps a module name to a path + // description: + // An unregistered module is given the default path of ../[module], + // relative to Dojo root. For example, module acme is mapped to + // ../acme. If you want to use a different module name, use + // dojo.registerModulePath. + // example: + // If your dojo.js is located at this location in the web root: + // | /myapp/js/dojo/dojo/dojo.js + // and your modules are located at: + // | /myapp/js/foo/bar.js + // | /myapp/js/foo/baz.js + // | /myapp/js/foo/thud/xyzzy.js + // Your application can tell Dojo to locate the "foo" namespace by calling: + // | dojo.registerModulePath("foo", "../../foo"); + // At which point you can then use dojo.require() to load the + // modules (assuming they provide() the same things which are + // required). The full code might be: + // | <script type="text/javascript" + // | src="/myapp/js/dojo/dojo/dojo.js"></script> + // | <script type="text/javascript"> + // | dojo.registerModulePath("foo", "../../foo"); + // | dojo.require("foo.bar"); + // | dojo.require("foo.baz"); + // | dojo.require("foo.thud.xyzzy"); + // | </script> + d._modulePrefixes[module] = { name: module, value: prefix }; + } + + dojo.requireLocalization = function(/*String*/moduleName, /*String*/bundleName, /*String?*/locale, /*String?*/availableFlatLocales){ + // summary: + // Declares translated resources and loads them if necessary, in the + // same style as dojo.require. Contents of the resource bundle are + // typically strings, but may be any name/value pair, represented in + // JSON format. See also `dojo.i18n.getLocalization`. + // + // description: + // Load translated resource bundles provided underneath the "nls" + // directory within a package. Translated resources may be located in + // different packages throughout the source tree. + // + // Each directory is named for a locale as specified by RFC 3066, + // (http://www.ietf.org/rfc/rfc3066.txt), normalized in lowercase. + // Note that the two bundles in the example do not define all the + // same variants. For a given locale, bundles will be loaded for + // that locale and all more general locales above it, including a + // fallback at the root directory. For example, a declaration for + // the "de-at" locale will first load `nls/de-at/bundleone.js`, + // then `nls/de/bundleone.js` and finally `nls/bundleone.js`. The + // data will be flattened into a single Object so that lookups + // will follow this cascading pattern. An optional build step can + // preload the bundles to avoid data redundancy and the multiple + // network hits normally required to load these resources. + // + // moduleName: + // name of the package containing the "nls" directory in which the + // bundle is found + // + // bundleName: + // bundle name, i.e. the filename without the '.js' suffix + // + // locale: + // the locale to load (optional) By default, the browser's user + // locale as defined by dojo.locale + // + // availableFlatLocales: + // A comma-separated list of the available, flattened locales for this + // bundle. This argument should only be set by the build process. + // + // example: + // A particular widget may define one or more resource bundles, + // structured in a program as follows, where moduleName is + // mycode.mywidget and bundleNames available include bundleone and + // bundletwo: + // | ... + // | mycode/ + // | mywidget/ + // | nls/ + // | bundleone.js (the fallback translation, English in this example) + // | bundletwo.js (also a fallback translation) + // | de/ + // | bundleone.js + // | bundletwo.js + // | de-at/ + // | bundleone.js + // | en/ + // | (empty; use the fallback translation) + // | en-us/ + // | bundleone.js + // | en-gb/ + // | bundleone.js + // | es/ + // | bundleone.js + // | bundletwo.js + // | ...etc + // | ... + // + + d.require("dojo.i18n"); + d.i18n._requireLocalization.apply(d.hostenv, arguments); + }; + + + var ore = new RegExp("^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$"); + var ire = new RegExp("^((([^\\[:]+):)?([^@]+)@)?(\\[([^\\]]+)\\]|([^\\[:]*))(:([0-9]+))?$"); + + dojo._Url = function(/*dojo._Url||String...*/){ + // summary: + // Constructor to create an object representing a URL. + // It is marked as private, since we might consider removing + // or simplifying it. + // description: + // Each argument is evaluated in order relative to the next until + // a canonical uri is produced. To get an absolute Uri relative to + // the current document use: + // new dojo._Url(document.baseURI, url) + + var n = null; + + var _a = arguments; + var uri = [_a[0]]; + // resolve uri components relative to each other + for(var i = 1; i<_a.length; i++){ + if(!_a[i]){ continue; } + + // Safari doesn't support this.constructor so we have to be explicit + // FIXME: Tracked (and fixed) in Webkit bug 3537. + // http://bugs.webkit.org/show_bug.cgi?id=3537 + var relobj = new d._Url(_a[i]+""); + var uriobj = new d._Url(uri[0]+""); + + if( + relobj.path == "" && + !relobj.scheme && + !relobj.authority && + !relobj.query + ){ + if(relobj.fragment != n){ + uriobj.fragment = relobj.fragment; + } + relobj = uriobj; + }else if(!relobj.scheme){ + relobj.scheme = uriobj.scheme; + + if(!relobj.authority){ + relobj.authority = uriobj.authority; + + if(relobj.path.charAt(0) != "/"){ + var path = uriobj.path.substring(0, + uriobj.path.lastIndexOf("/") + 1) + relobj.path; + + var segs = path.split("/"); + for(var j = 0; j < segs.length; j++){ + if(segs[j] == "."){ + // flatten "./" references + if(j == segs.length - 1){ + segs[j] = ""; + }else{ + segs.splice(j, 1); + j--; + } + }else if(j > 0 && !(j == 1 && segs[0] == "") && + segs[j] == ".." && segs[j-1] != ".."){ + // flatten "../" references + if(j == (segs.length - 1)){ + segs.splice(j, 1); + segs[j - 1] = ""; + }else{ + segs.splice(j - 1, 2); + j -= 2; + } + } + } + relobj.path = segs.join("/"); + } + } + } + + uri = []; + if(relobj.scheme){ + uri.push(relobj.scheme, ":"); + } + if(relobj.authority){ + uri.push("//", relobj.authority); + } + uri.push(relobj.path); + if(relobj.query){ + uri.push("?", relobj.query); + } + if(relobj.fragment){ + uri.push("#", relobj.fragment); + } + } + + this.uri = uri.join(""); + + // break the uri into its main components + var r = this.uri.match(ore); + + this.scheme = r[2] || (r[1] ? "" : n); + this.authority = r[4] || (r[3] ? "" : n); + this.path = r[5]; // can never be undefined + this.query = r[7] || (r[6] ? "" : n); + this.fragment = r[9] || (r[8] ? "" : n); + + if(this.authority != n){ + // server based naming authority + r = this.authority.match(ire); + + this.user = r[3] || n; + this.password = r[4] || n; + this.host = r[6] || r[7]; // ipv6 || ipv4 + this.port = r[9] || n; + } + } + + dojo._Url.prototype.toString = function(){ return this.uri; }; + + dojo.moduleUrl = function(/*String*/module, /*dojo._Url||String*/url){ + // summary: + // Returns a `dojo._Url` object relative to a module. + // example: + // | var pngPath = dojo.moduleUrl("acme","images/small.png"); + // | // list the object properties + // | // create an image and set it's source to pngPath's value: + // | var img = document.createElement("img"); + // | // NOTE: we assign the string representation of the url object + // | img.src = pngPath.toString(); + // | // add our image to the document + // | dojo.body().appendChild(img); + // example: + // you may de-reference as far as you like down the package + // hierarchy. This is sometimes handy to avoid lenghty relative + // urls or for building portable sub-packages. In this example, + // the `acme.widget` and `acme.util` directories may be located + // under different roots (see `dojo.registerModulePath`) but the + // the modules which reference them can be unaware of their + // relative locations on the filesystem: + // | // somewhere in a configuration block + // | dojo.registerModulePath("acme.widget", "../../acme/widget"); + // | dojo.registerModulePath("acme.util", "../../util"); + // | + // | // ... + // | + // | // code in a module using acme resources + // | var tmpltPath = dojo.moduleUrl("acme.widget","templates/template.html"); + // | var dataPath = dojo.moduleUrl("acme.util","resources/data.json"); + + var loc = d._getModuleSymbols(module).join('/'); + if(!loc){ return null; } + if(loc.lastIndexOf("/") != loc.length-1){ + loc += "/"; + } + + //If the path is an absolute path (starts with a / or is on another + //domain/xdomain) then don't add the baseUrl. + var colonIndex = loc.indexOf(":"); + if(loc.charAt(0) != "/" && (colonIndex == -1 || colonIndex > loc.indexOf("/"))){ + loc = d.baseUrl + loc; + } + + return new d._Url(loc, url); // String + } +})(); + +/*===== +dojo.isBrowser = { + // example: + // | if(dojo.isBrowser){ ... } +}; + +dojo.isFF = { + // example: + // | if(dojo.isFF > 1){ ... } +}; + +dojo.isIE = { + // example: + // | if(dojo.isIE > 6){ + // | // we are IE7 + // | } +}; + +dojo.isSafari = { + // example: + // | if(dojo.isSafari){ ... } + // example: + // Detect iPhone: + // | if(dojo.isSafari && navigator.userAgent.indexOf("iPhone") != -1){ + // | // we are iPhone. Note, iPod touch reports "iPod" above and fails this test. + // | } +}; + +dojo = { + // isBrowser: Boolean + // True if the client is a web-browser + isBrowser: true, + // isFF: Number | undefined + // Version as a Number if client is FireFox. undefined otherwise. Corresponds to + // major detected FireFox version (1.5, 2, 3, etc.) + isFF: 2, + // isIE: Number | undefined + // Version as a Number if client is MSIE(PC). undefined otherwise. Corresponds to + // major detected IE version (6, 7, 8, etc.) + isIE: 6, + // isKhtml: Number | undefined + // Version as a Number if client is a KHTML browser. undefined otherwise. Corresponds to major + // detected version. + isKhtml: 0, + // isWebKit: Number | undefined + // Version as a Number if client is a WebKit-derived browser (Konqueror, + // Safari, Chrome, etc.). undefined otherwise. + isWebKit: 0, + // isMozilla: Number | undefined + // Version as a Number if client is a Mozilla-based browser (Firefox, + // SeaMonkey). undefined otherwise. Corresponds to major detected version. + isMozilla: 0, + // isOpera: Number | undefined + // Version as a Number if client is Opera. undefined otherwise. Corresponds to + // major detected version. + isOpera: 0, + // isSafari: Number | undefined + // Version as a Number if client is Safari or iPhone. undefined otherwise. + isSafari: 0 + // isChrome: Number | undefined + // Version as a Number if client is Chrome browser. undefined otherwise. + isChrome: 0 +} +=====*/ + +if(typeof window != 'undefined'){ + dojo.isBrowser = true; + dojo._name = "browser"; + + + // attempt to figure out the path to dojo if it isn't set in the config + (function(){ + var d = dojo; + + // this is a scope protection closure. We set browser versions and grab + // the URL we were loaded from here. + + // grab the node we were loaded from + if(document && document.getElementsByTagName){ + var scripts = document.getElementsByTagName("script"); + var rePkg = /dojo(\.xd)?\.js(\W|$)/i; + for(var i = 0; i < scripts.length; i++){ + var src = scripts[i].getAttribute("src"); + if(!src){ continue; } + var m = src.match(rePkg); + if(m){ + // find out where we came from + if(!d.config.baseUrl){ + d.config.baseUrl = src.substring(0, m.index); + } + // and find out if we need to modify our behavior + var cfg = scripts[i].getAttribute("djConfig"); + if(cfg){ + var cfgo = eval("({ "+cfg+" })"); + for(var x in cfgo){ + dojo.config[x] = cfgo[x]; + } + } + break; // "first Dojo wins" + } + } + } + d.baseUrl = d.config.baseUrl; + + // fill in the rendering support information in dojo.render.* + var n = navigator; + var dua = n.userAgent, + dav = n.appVersion, + tv = parseFloat(dav); + + if(dua.indexOf("Opera") >= 0){ d.isOpera = tv; } + if(dua.indexOf("AdobeAIR") >= 0){ d.isAIR = 1; } + d.isKhtml = (dav.indexOf("Konqueror") >= 0) ? tv : 0; + d.isWebKit = parseFloat(dua.split("WebKit/")[1]) || undefined; + d.isChrome = parseFloat(dua.split("Chrome/")[1]) || undefined; + + // safari detection derived from: + // http://developer.apple.com/internet/safari/faq.html#anchor2 + // http://developer.apple.com/internet/safari/uamatrix.html + var index = Math.max(dav.indexOf("WebKit"), dav.indexOf("Safari"), 0); + if(index && !dojo.isChrome){ + // try to grab the explicit Safari version first. If we don't get + // one, look for less than 419.3 as the indication that we're on something + // "Safari 2-ish". + d.isSafari = parseFloat(dav.split("Version/")[1]); + if(!d.isSafari || parseFloat(dav.substr(index + 7)) <= 419.3){ + d.isSafari = 2; + } + } + + if(dua.indexOf("Gecko") >= 0 && !d.isKhtml && !d.isWebKit){ d.isMozilla = d.isMoz = tv; } + if(d.isMoz){ + //We really need to get away from this. Consider a sane isGecko approach for the future. + d.isFF = parseFloat(dua.split("Firefox/")[1] || dua.split("Minefield/")[1] || dua.split("Shiretoko/")[1]) || undefined; + } + if(document.all && !d.isOpera){ + d.isIE = parseFloat(dav.split("MSIE ")[1]) || undefined; + //In cases where the page has an HTTP header or META tag with + //X-UA-Compatible, then it is in emulation mode, for a previous + //version. Make sure isIE reflects the desired version. + //document.documentMode of 5 means quirks mode. + if(d.isIE >= 8 && document.documentMode != 5){ + d.isIE = document.documentMode; + } + } + + //Workaround to get local file loads of dojo to work on IE 7 + //by forcing to not use native xhr. + if(dojo.isIE && window.location.protocol === "file:"){ + dojo.config.ieForceActiveXXhr=true; + } + + var cm = document.compatMode; + d.isQuirks = cm == "BackCompat" || cm == "QuirksMode" || d.isIE < 6; + + // TODO: is the HTML LANG attribute relevant? + d.locale = dojo.config.locale || (d.isIE ? n.userLanguage : n.language).toLowerCase(); + + // These are in order of decreasing likelihood; this will change in time. + d._XMLHTTP_PROGIDS = ['Msxml2.XMLHTTP', 'Microsoft.XMLHTTP', 'Msxml2.XMLHTTP.4.0']; + + d._xhrObj = function(){ + // summary: + // does the work of portably generating a new XMLHTTPRequest object. + var http, last_e; + if(!dojo.isIE || !dojo.config.ieForceActiveXXhr){ + try{ http = new XMLHttpRequest(); }catch(e){} + } + if(!http){ + for(var i=0; i<3; ++i){ + var progid = d._XMLHTTP_PROGIDS[i]; + try{ + http = new ActiveXObject(progid); + }catch(e){ + last_e = e; + } + + if(http){ + d._XMLHTTP_PROGIDS = [progid]; // so faster next time + break; + } + } + } + + if(!http){ + throw new Error("XMLHTTP not available: "+last_e); + } + + return http; // XMLHTTPRequest instance + } + + d._isDocumentOk = function(http){ + var stat = http.status || 0; + return (stat >= 200 && stat < 300) || // Boolean + stat == 304 || // allow any 2XX response code + stat == 1223 || // get it out of the cache + (!stat && (location.protocol=="file:" || location.protocol=="chrome:") ); // Internet Explorer mangled the status code + } + + //See if base tag is in use. + //This is to fix http://trac.dojotoolkit.org/ticket/3973, + //but really, we need to find out how to get rid of the dojo._Url reference + //below and still have DOH work with the dojo.i18n test following some other + //test that uses the test frame to load a document (trac #2757). + //Opera still has problems, but perhaps a larger issue of base tag support + //with XHR requests (hasBase is true, but the request is still made to document + //path, not base path). + var owloc = window.location+""; + var base = document.getElementsByTagName("base"); + var hasBase = (base && base.length > 0); + + d._getText = function(/*URI*/ uri, /*Boolean*/ fail_ok){ + // summary: Read the contents of the specified uri and return those contents. + // uri: + // A relative or absolute uri. If absolute, it still must be in + // the same "domain" as we are. + // fail_ok: + // Default false. If fail_ok and loading fails, return null + // instead of throwing. + // returns: The response text. null is returned when there is a + // failure and failure is okay (an exception otherwise) + + // NOTE: must be declared before scope switches ie. this._xhrObj() + var http = this._xhrObj(); + + if(!hasBase && dojo._Url){ + uri = (new dojo._Url(owloc, uri)).toString(); + } + + if(d.config.cacheBust){ + //Make sure we have a string before string methods are used on uri + uri += ""; + uri += (uri.indexOf("?") == -1 ? "?" : "&") + String(d.config.cacheBust).replace(/\W+/g,""); + } + + http.open('GET', uri, false); + try{ + http.send(null); + if(!d._isDocumentOk(http)){ + var err = Error("Unable to load "+uri+" status:"+ http.status); + err.status = http.status; + err.responseText = http.responseText; + throw err; + } + }catch(e){ + if(fail_ok){ return null; } // null + // rethrow the exception + throw e; + } + return http.responseText; // String + } + + + var _w = window; + var _handleNodeEvent = function(/*String*/evtName, /*Function*/fp){ + // summary: + // non-destructively adds the specified function to the node's + // evtName handler. + // evtName: should be in the form "onclick" for "onclick" handlers. + // Make sure you pass in the "on" part. + var oldHandler = _w[evtName] || function(){}; + _w[evtName] = function(){ + fp.apply(_w, arguments); + oldHandler.apply(_w, arguments); + }; + }; + + + d._windowUnloaders = []; + + d.windowUnloaded = function(){ + // summary: + // signal fired by impending window destruction. You may use + // dojo.addOnWindowUnload() to register a listener for this + // event. NOTE: if you wish to dojo.connect() to this method + // to perform page/application cleanup, be aware that this + // event WILL NOT fire if no handler has been registered with + // dojo.addOnWindowUnload. This behavior started in Dojo 1.3. + // Previous versions always triggered dojo.windowUnloaded. See + // dojo.addOnWindowUnload for more info. + var mll = d._windowUnloaders; + while(mll.length){ + (mll.pop())(); + } + }; + + var _onWindowUnloadAttached = 0; + d.addOnWindowUnload = function(/*Object?|Function?*/obj, /*String|Function?*/functionName){ + // summary: + // registers a function to be triggered when window.onunload + // fires. + // description: + // The first time that addOnWindowUnload is called Dojo + // will register a page listener to trigger your unload + // handler with. Note that registering these handlers may + // destory "fastback" page caching in browsers that support + // it. Be careful trying to modify the DOM or access + // JavaScript properties during this phase of page unloading: + // they may not always be available. Consider + // dojo.addOnUnload() if you need to modify the DOM or do + // heavy JavaScript work since it fires at the eqivalent of + // the page's "onbeforeunload" event. + // example: + // | dojo.addOnWindowUnload(functionPointer) + // | dojo.addOnWindowUnload(object, "functionName"); + // | dojo.addOnWindowUnload(object, function(){ /* ... */}); + + d._onto(d._windowUnloaders, obj, functionName); + if(!_onWindowUnloadAttached){ + _onWindowUnloadAttached = 1; + _handleNodeEvent("onunload", d.windowUnloaded); + } + }; + + var _onUnloadAttached = 0; + d.addOnUnload = function(/*Object?|Function?*/obj, /*String|Function?*/functionName){ + // summary: + // registers a function to be triggered when the page unloads. + // description: + // The first time that addOnUnload is called Dojo will + // register a page listener to trigger your unload handler + // with. + // + // In a browser enviroment, the functions will be triggered + // during the window.onbeforeunload event. Be careful of doing + // too much work in an unload handler. onbeforeunload can be + // triggered if a link to download a file is clicked, or if + // the link is a javascript: link. In these cases, the + // onbeforeunload event fires, but the document is not + // actually destroyed. So be careful about doing destructive + // operations in a dojo.addOnUnload callback. + // + // Further note that calling dojo.addOnUnload will prevent + // browsers from using a "fast back" cache to make page + // loading via back button instantaneous. + // example: + // | dojo.addOnUnload(functionPointer) + // | dojo.addOnUnload(object, "functionName") + // | dojo.addOnUnload(object, function(){ /* ... */}); + + d._onto(d._unloaders, obj, functionName); + if(!_onUnloadAttached){ + _onUnloadAttached = 1; + _handleNodeEvent("onbeforeunload", dojo.unloaded); + } + }; + + })(); + + dojo._initFired = false; + // BEGIN DOMContentLoaded, from Dean Edwards (http://dean.edwards.name/weblog/2006/06/again/) + dojo._loadInit = function(e){ + dojo._initFired = true; + // allow multiple calls, only first one will take effect + // A bug in khtml calls events callbacks for document for event which isnt supported + // for example a created contextmenu event calls DOMContentLoaded, workaround + var type = e && e.type ? e.type.toLowerCase() : "load"; + if(arguments.callee.initialized || (type != "domcontentloaded" && type != "load")){ return; } + arguments.callee.initialized = true; + if("_khtmlTimer" in dojo){ + clearInterval(dojo._khtmlTimer); + delete dojo._khtmlTimer; + } + + if(dojo._inFlightCount == 0){ + dojo._modulesLoaded(); + } + } + + if(!dojo.config.afterOnLoad){ + // START DOMContentLoaded + // Mozilla and Opera 9 expose the event we could use + if(document.addEventListener){ + // NOTE: + // due to a threading issue in Firefox 2.0, we can't enable + // DOMContentLoaded on that platform. For more information, see: + // http://trac.dojotoolkit.org/ticket/1704 + if(dojo.isWebKit > 525 || dojo.isOpera || dojo.isFF >= 3 || (dojo.isMoz && dojo.config.enableMozDomContentLoaded === true)){ + document.addEventListener("DOMContentLoaded", dojo._loadInit, null); + } + + // mainly for Opera 8.5, won't be fired if DOMContentLoaded fired already. + // also used for Mozilla because of trac #1640 + window.addEventListener("load", dojo._loadInit, null); + } + + if(dojo.isAIR){ + window.addEventListener("load", dojo._loadInit, null); + }else if((dojo.isWebKit < 525) || dojo.isKhtml){ + dojo._khtmlTimer = setInterval(function(){ + if(/loaded|complete/.test(document.readyState)){ + dojo._loadInit(); // call the onload handler + } + }, 10); + } + // END DOMContentLoaded + } + + if(dojo.isIE){ + // for Internet Explorer. readyState will not be achieved on init + // call, but dojo doesn't need it however, we'll include it + // because we don't know if there are other functions added that + // might. Note that this has changed because the build process + // strips all comments -- including conditional ones. + if(!dojo.config.afterOnLoad){ + document.write('<scr'+'ipt defer src="//:" ' + + 'onreadystatechange="if(this.readyState==\'complete\'){' + dojo._scopeName + '._loadInit();}">' + + '</scr'+'ipt>' + ); + } + + try{ + document.namespaces.add("v","urn:schemas-microsoft-com:vml"); + document.createStyleSheet().addRule("v\\:*", "behavior:url(#default#VML); display:inline-block"); + }catch(e){} + } + + + /* + OpenAjax.subscribe("OpenAjax", "onload", function(){ + if(dojo._inFlightCount == 0){ + dojo._modulesLoaded(); + } + }); + + OpenAjax.subscribe("OpenAjax", "onunload", function(){ + dojo.unloaded(); + }); + */ +} //if (typeof window != 'undefined') + +//Register any module paths set up in djConfig. Need to do this +//in the hostenvs since hostenv_browser can read djConfig from a +//script tag's attribute. +(function(){ + var mp = dojo.config["modulePaths"]; + if(mp){ + for(var param in mp){ + dojo.registerModulePath(param, mp[param]); + } + } +})(); + +//Load debug code if necessary. +if(dojo.config.isDebug){ + dojo.require("dojo._firebug.firebug"); +} + +if(dojo.config.debugAtAllCosts){ + dojo.config.useXDomain = true; + dojo.require("dojo._base._loader.loader_xd"); + dojo.require("dojo._base._loader.loader_debug"); + dojo.require("dojo.i18n"); +} + +if(!dojo._hasResource["dojo._base.lang"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.lang"] = true; +dojo.provide("dojo._base.lang"); + +// Crockford (ish) functions + +dojo.isString = function(/*anything*/ it){ + // summary: + // Return true if it is a String + return !!arguments.length && it != null && (typeof it == "string" || it instanceof String); // Boolean +} + +dojo.isArray = function(/*anything*/ it){ + // summary: + // Return true if it is an Array + return it && (it instanceof Array || typeof it == "array"); // Boolean +} + +/*===== +dojo.isFunction = function(it){ + // summary: Return true if it is a Function + // it: anything + return; // Boolean +} +=====*/ + +dojo.isFunction = (function(){ + var _isFunction = function(/*anything*/ it){ + var t = typeof it; // must evaluate separately due to bizarre Opera bug. See #8937 + return it && (t == "function" || it instanceof Function); // Boolean + }; + + return dojo.isSafari ? + // only slow this down w/ gratuitious casting in Safari (not WebKit) + function(/*anything*/ it){ + if(typeof it == "function" && it == "[object NodeList]"){ return false; } + return _isFunction(it); // Boolean + } : _isFunction; +})(); + +dojo.isObject = function(/*anything*/ it){ + // summary: + // Returns true if it is a JavaScript object (or an Array, a Function + // or null) + return it !== undefined && + (it === null || typeof it == "object" || dojo.isArray(it) || dojo.isFunction(it)); // Boolean +} + +dojo.isArrayLike = function(/*anything*/ it){ + // summary: + // similar to dojo.isArray() but more permissive + // description: + // Doesn't strongly test for "arrayness". Instead, settles for "isn't + // a string or number and has a length property". Arguments objects + // and DOM collections will return true when passed to + // dojo.isArrayLike(), but will return false when passed to + // dojo.isArray(). + // returns: + // If it walks like a duck and quacks like a duck, return `true` + var d = dojo; + return it && it !== undefined && // Boolean + // keep out built-in constructors (Number, String, ...) which have length + // properties + !d.isString(it) && !d.isFunction(it) && + !(it.tagName && it.tagName.toLowerCase() == 'form') && + (d.isArray(it) || isFinite(it.length)); +} + +dojo.isAlien = function(/*anything*/ it){ + // summary: + // Returns true if it is a built-in function or some other kind of + // oddball that *should* report as a function but doesn't + return it && !dojo.isFunction(it) && /\{\s*\[native code\]\s*\}/.test(String(it)); // Boolean +} + +dojo.extend = function(/*Object*/ constructor, /*Object...*/ props){ + // summary: + // Adds all properties and methods of props to constructor's + // prototype, making them available to all instances created with + // constructor. + for(var i=1, l=arguments.length; i<l; i++){ + dojo._mixin(constructor.prototype, arguments[i]); + } + return constructor; // Object +} + +dojo._hitchArgs = function(scope, method /*,...*/){ + var pre = dojo._toArray(arguments, 2); + var named = dojo.isString(method); + return function(){ + // arrayify arguments + var args = dojo._toArray(arguments); + // locate our method + var f = named ? (scope||dojo.global)[method] : method; + // invoke with collected args + return f && f.apply(scope || this, pre.concat(args)); // mixed + } // Function +} + +dojo.hitch = function(/*Object*/scope, /*Function|String*/method /*,...*/){ + // summary: + // Returns a function that will only ever execute in the a given scope. + // This allows for easy use of object member functions + // in callbacks and other places in which the "this" keyword may + // otherwise not reference the expected scope. + // Any number of default positional arguments may be passed as parameters + // beyond "method". + // Each of these values will be used to "placehold" (similar to curry) + // for the hitched function. + // scope: + // The scope to use when method executes. If method is a string, + // scope is also the object containing method. + // method: + // A function to be hitched to scope, or the name of the method in + // scope to be hitched. + // example: + // | dojo.hitch(foo, "bar")(); + // runs foo.bar() in the scope of foo + // example: + // | dojo.hitch(foo, myFunction); + // returns a function that runs myFunction in the scope of foo + if(arguments.length > 2){ + return dojo._hitchArgs.apply(dojo, arguments); // Function + } + if(!method){ + method = scope; + scope = null; + } + if(dojo.isString(method)){ + scope = scope || dojo.global; + if(!scope[method]){ throw(['dojo.hitch: scope["', method, '"] is null (scope="', scope, '")'].join('')); } + return function(){ return scope[method].apply(scope, arguments || []); }; // Function + } + return !scope ? method : function(){ return method.apply(scope, arguments || []); }; // Function +} + +/*===== +dojo.delegate = function(obj, props){ + // summary: + // Returns a new object which "looks" to obj for properties which it + // does not have a value for. Optionally takes a bag of properties to + // seed the returned object with initially. + // description: + // This is a small implementaton of the Boodman/Crockford delegation + // pattern in JavaScript. An intermediate object constructor mediates + // the prototype chain for the returned object, using it to delegate + // down to obj for property lookup when object-local lookup fails. + // This can be thought of similarly to ES4's "wrap", save that it does + // not act on types but rather on pure objects. + // obj: + // The object to delegate to for properties not found directly on the + // return object or in props. + // props: + // an object containing properties to assign to the returned object + // returns: + // an Object of anonymous type + // example: + // | var foo = { bar: "baz" }; + // | var thinger = dojo.delegate(foo, { thud: "xyzzy"}); + // | thinger.bar == "baz"; // delegated to foo + // | foo.thud == undefined; // by definition + // | thinger.thud == "xyzzy"; // mixed in from props + // | foo.bar = "thonk"; + // | thinger.bar == "thonk"; // still delegated to foo's bar +} +=====*/ + +dojo.delegate = dojo._delegate = (function(){ + // boodman/crockford delegation w/ cornford optimization + function TMP(){} + return function(obj, props){ + TMP.prototype = obj; + var tmp = new TMP(); + if(props){ + dojo._mixin(tmp, props); + } + return tmp; // Object + } +})(); + +/*===== +dojo._toArray = function(obj, offset, startWith){ + // summary: + // Converts an array-like object (i.e. arguments, DOMCollection) to an + // array. Returns a new Array with the elements of obj. + // obj: Object + // the object to "arrayify". We expect the object to have, at a + // minimum, a length property which corresponds to integer-indexed + // properties. + // offset: Number? + // the location in obj to start iterating from. Defaults to 0. + // Optional. + // startWith: Array? + // An array to pack with the properties of obj. If provided, + // properties in obj are appended at the end of startWith and + // startWith is the returned array. +} +=====*/ + +(function(){ + var efficient = function(obj, offset, startWith){ + return (startWith||[]).concat(Array.prototype.slice.call(obj, offset||0)); + }; + + var slow = function(obj, offset, startWith){ + var arr = startWith||[]; + for(var x = offset || 0; x < obj.length; x++){ + arr.push(obj[x]); + } + return arr; + }; + + dojo._toArray = + dojo.isIE ? function(obj){ + return ((obj.item) ? slow : efficient).apply(this, arguments); + } : + efficient; + +})(); + +dojo.partial = function(/*Function|String*/method /*, ...*/){ + // summary: + // similar to hitch() except that the scope object is left to be + // whatever the execution context eventually becomes. + // description: + // Calling dojo.partial is the functional equivalent of calling: + // | dojo.hitch(null, funcName, ...); + var arr = [ null ]; + return dojo.hitch.apply(dojo, arr.concat(dojo._toArray(arguments))); // Function +} + +dojo.clone = function(/*anything*/ o){ + // summary: + // Clones objects (including DOM nodes) and all children. + // Warning: do not clone cyclic structures. + if(!o){ return o; } + if(dojo.isArray(o)){ + var r = []; + for(var i = 0; i < o.length; ++i){ + r.push(dojo.clone(o[i])); + } + return r; // Array + } + if(!dojo.isObject(o)){ + return o; /*anything*/ + } + if(o.nodeType && o.cloneNode){ // isNode + return o.cloneNode(true); // Node + } + if(o instanceof Date){ + return new Date(o.getTime()); // Date + } + // Generic objects + r = new o.constructor(); // specific to dojo.declare()'d classes! + for(i in o){ + if(!(i in r) || r[i] != o[i]){ + r[i] = dojo.clone(o[i]); + } + } + return r; // Object +} + +/*===== +dojo.trim = function(str){ + // summary: + // Trims whitespace from both sides of the string + // str: String + // String to be trimmed + // returns: String + // Returns the trimmed string + // description: + // This version of trim() was selected for inclusion into the base due + // to its compact size and relatively good performance + // (see [Steven Levithan's blog](http://blog.stevenlevithan.com/archives/faster-trim-javascript) + // Uses String.prototype.trim instead, if available. + // The fastest but longest version of this function is located at + // dojo.string.trim() + return ""; // String +} +=====*/ + +dojo.trim = String.prototype.trim ? + function(str){ return str.trim(); } : + function(str){ return str.replace(/^\s\s*/, '').replace(/\s\s*$/, ''); }; + +} + +if(!dojo._hasResource["dojo._base.declare"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.declare"] = true; +dojo.provide("dojo._base.declare"); + + +// this file courtesy of the TurboAjax Group, licensed under a Dojo CLA + +dojo.declare = function(/*String*/ className, /*Function|Function[]*/ superclass, /*Object*/ props){ + // summary: + // Create a feature-rich constructor from compact notation + // className: + // The name of the constructor (loosely, a "class") + // stored in the "declaredClass" property in the created prototype + // superclass: + // May be null, a Function, or an Array of Functions. If an array, + // the first element is used as the prototypical ancestor and + // any following Functions become mixin ancestors. + // props: + // An object whose properties are copied to the + // created prototype. + // Add an instance-initialization function by making it a property + // named "constructor". + // description: + // Create a constructor using a compact notation for inheritance and + // prototype extension. + // + // All superclasses (including mixins) must be Functions (not simple Objects). + // + // Mixin ancestors provide a type of multiple inheritance. Prototypes of mixin + // ancestors are copied to the new class: changes to mixin prototypes will + // not affect classes to which they have been mixed in. + // + // "className" is cached in "declaredClass" property of the new class. + // + // example: + // | dojo.declare("my.classes.bar", my.classes.foo, { + // | // properties to be added to the class prototype + // | someValue: 2, + // | // initialization function + // | constructor: function(){ + // | this.myComplicatedObject = new ReallyComplicatedObject(); + // | }, + // | // other functions + // | someMethod: function(){ + // | doStuff(); + // | } + // | ); + + // process superclass argument + var dd = arguments.callee, mixins; + if(dojo.isArray(superclass)){ + mixins = superclass; + superclass = mixins.shift(); + } + // construct intermediate classes for mixins + if(mixins){ + dojo.forEach(mixins, function(m, i){ + if(!m){ throw(className + ": mixin #" + i + " is null"); } // It's likely a required module is not loaded + superclass = dd._delegate(superclass, m); + }); + } + // create constructor + var ctor = dd._delegate(superclass); + // extend with "props" + props = props || {}; + ctor.extend(props); + // more prototype decoration + dojo.extend(ctor, {declaredClass: className, _constructor: props.constructor/*, preamble: null*/}); + // special help for IE + ctor.prototype.constructor = ctor; + // create named reference + return dojo.setObject(className, ctor); // Function +}; + +dojo.mixin(dojo.declare, { + _delegate: function(base, mixin){ + var bp = (base||0).prototype, mp = (mixin||0).prototype, dd=dojo.declare; + // fresh constructor, fresh prototype + var ctor = dd._makeCtor(); + // cache ancestry + dojo.mixin(ctor, {superclass: bp, mixin: mp, extend: dd._extend}); + // chain prototypes + if(base){ctor.prototype = dojo._delegate(bp);} + // add mixin and core + dojo.extend(ctor, dd._core, mp||0, {_constructor: null, preamble: null}); + // special help for IE + ctor.prototype.constructor = ctor; + // name this class for debugging + ctor.prototype.declaredClass = (bp||0).declaredClass + '_' + (mp||0).declaredClass; + return ctor; + }, + _extend: function(props){ + var i, fn; + for(i in props){ if(dojo.isFunction(fn=props[i]) && !0[i]){fn.nom=i;fn.ctor=this;} } + dojo.extend(this, props); + }, + _makeCtor: function(){ + // we have to make a function, but don't want to close over anything + return function(){ this._construct(arguments); }; + }, + _core: { + _construct: function(args){ + var c=args.callee, s=c.superclass, ct=s&&s.constructor, m=c.mixin, mct=m&&m.constructor, a=args, ii, fn; + // side-effect of = used on purpose here, lint may complain, don't try this at home + if(a[0]){ + // FIXME: preambles for each mixin should be allowed + // FIXME: + // should we allow the preamble here NOT to modify the + // default args, but instead to act on each mixin + // independently of the class instance being constructed + // (for impedence matching)? + + // allow any first argument w/ a "preamble" property to act as a + // class preamble (not exclusive of the prototype preamble) + if(/*dojo.isFunction*/((fn = a[0].preamble))){ + a = fn.apply(this, a) || a; + } + } + // prototype preamble + if((fn = c.prototype.preamble)){a = fn.apply(this, a) || a;} + // FIXME: + // need to provide an optional prototype-settable + // "_explicitSuper" property which disables this + // initialize superclass + if(ct&&ct.apply){ct.apply(this, a);} + // initialize mixin + if(mct&&mct.apply){mct.apply(this, a);} + // initialize self + if((ii=c.prototype._constructor)){ii.apply(this, args);} + // post construction + if(this.constructor.prototype==c.prototype && (ct=this.postscript)){ ct.apply(this, args); } + }, + _findMixin: function(mixin){ + var c = this.constructor, p, m; + while(c){ + p = c.superclass; + m = c.mixin; + if(m==mixin || (m instanceof mixin.constructor)){return p;} + if(m && m._findMixin && (m=m._findMixin(mixin))){return m;} + c = p && p.constructor; + } + }, + _findMethod: function(name, method, ptype, has){ + // consciously trading readability for bytes and speed in this low-level method + var p=ptype, c, m, f; + do{ + c = p.constructor; + m = c.mixin; + // find method by name in our mixin ancestor + if(m && (m=this._findMethod(name, method, m, has))){return m;} + // if we found a named method that either exactly-is or exactly-is-not 'method' + if((f=p[name])&&(has==(f==method))){return p;} + // ascend chain + p = c.superclass; + }while(p); + // if we couldn't find an ancestor in our primary chain, try a mixin chain + return !has && (p=this._findMixin(ptype)) && this._findMethod(name, method, p, has); + }, + inherited: function(name, args, newArgs){ + // optionalize name argument + var a = arguments; + if(!dojo.isString(a[0])){newArgs=args; args=name; name=args.callee.nom;} + a = newArgs||args; + var c = args.callee, p = this.constructor.prototype, fn, mp; + // if not an instance override + if(this[name] != c || p[name] == c){ + // start from memoized prototype, or + // find a prototype that has property 'name' == 'c' + mp = (c.ctor||0).superclass || this._findMethod(name, c, p, true); + if(!mp){throw(this.declaredClass + ': inherited method "' + name + '" mismatch');} + // find a prototype that has property 'name' != 'c' + p = this._findMethod(name, c, mp, false); + } + // we expect 'name' to be in prototype 'p' + fn = p && p[name]; + if(!fn){throw(mp.declaredClass + ': inherited method "' + name + '" not found');} + // if the function exists, invoke it in our scope + return fn.apply(this, a); + } + } +}); + +} + +if(!dojo._hasResource["dojo._base.connect"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.connect"] = true; +dojo.provide("dojo._base.connect"); + + +// this file courtesy of the TurboAjax Group, licensed under a Dojo CLA + +// low-level delegation machinery +dojo._listener = { + // create a dispatcher function + getDispatcher: function(){ + // following comments pulled out-of-line to prevent cloning them + // in the returned function. + // - indices (i) that are really in the array of listeners (ls) will + // not be in Array.prototype. This is the 'sparse array' trick + // that keeps us safe from libs that take liberties with built-in + // objects + // - listener is invoked with current scope (this) + return function(){ + var ap=Array.prototype, c=arguments.callee, ls=c._listeners, t=c.target; + // return value comes from original target function + var r = t && t.apply(this, arguments); + // make local copy of listener array so it is immutable during processing + var lls; + lls = [].concat(ls); + + // invoke listeners after target function + for(var i in lls){ + if(!(i in ap)){ + lls[i].apply(this, arguments); + } + } + // return value comes from original target function + return r; + } + }, + // add a listener to an object + add: function(/*Object*/ source, /*String*/ method, /*Function*/ listener){ + // Whenever 'method' is invoked, 'listener' will have the same scope. + // Trying to supporting a context object for the listener led to + // complexity. + // Non trivial to provide 'once' functionality here + // because listener could be the result of a dojo.hitch call, + // in which case two references to the same hitch target would not + // be equivalent. + source = source || dojo.global; + // The source method is either null, a dispatcher, or some other function + var f = source[method]; + // Ensure a dispatcher + if(!f||!f._listeners){ + var d = dojo._listener.getDispatcher(); + // original target function is special + d.target = f; + // dispatcher holds a list of listeners + d._listeners = []; + // redirect source to dispatcher + f = source[method] = d; + } + // The contract is that a handle is returned that can + // identify this listener for disconnect. + // + // The type of the handle is private. Here is it implemented as Integer. + // DOM event code has this same contract but handle is Function + // in non-IE browsers. + // + // We could have separate lists of before and after listeners. + return f._listeners.push(listener) ; /*Handle*/ + }, + // remove a listener from an object + remove: function(/*Object*/ source, /*String*/ method, /*Handle*/ handle){ + var f = (source||dojo.global)[method]; + // remember that handle is the index+1 (0 is not a valid handle) + if(f && f._listeners && handle--){ + delete f._listeners[handle]; + } + } +}; + +// Multiple delegation for arbitrary methods. + +// This unit knows nothing about DOM, +// but we include DOM aware +// documentation and dontFix +// argument here to help the autodocs. +// Actual DOM aware code is in event.js. + +dojo.connect = function(/*Object|null*/ obj, + /*String*/ event, + /*Object|null*/ context, + /*String|Function*/ method, + /*Boolean*/ dontFix){ + // summary: + // Create a link that calls one function when another executes. + // + // description: + // Connects method to event, so that after event fires, method + // does too. All connected functions are passed the same arguments as + // the event function was initially called with. You may connect as + // many methods to event as needed. + // + // event must be a string. If obj is null, dojo.global is used. + // + // null arguments may simply be omitted. + // + // obj[event] can resolve to a function or undefined (null). + // If obj[event] is null, it is assigned a function. + // + // The return value is a handle that is needed to + // remove this connection with dojo.disconnect. + // + // obj: + // The source object for the event function. + // Defaults to dojo.global if null. + // If obj is a DOM node, the connection is delegated + // to the DOM event manager (unless dontFix is true). + // + // event: + // String name of the event function in obj. + // I.e. identifies a property obj[event]. + // + // context: + // The object that method will receive as "this". + // + // If context is null and method is a function, then method + // inherits the context of event. + // + // If method is a string then context must be the source + // object object for method (context[method]). If context is null, + // dojo.global is used. + // + // method: + // A function reference, or name of a function in context. + // The function identified by method fires after event does. + // method receives the same arguments as the event. + // See context argument comments for information on method's scope. + // + // dontFix: + // If obj is a DOM node, set dontFix to true to prevent delegation + // of this connection to the DOM event manager. + // + // example: + // When obj.onchange(), do ui.update(): + // | dojo.connect(obj, "onchange", ui, "update"); + // | dojo.connect(obj, "onchange", ui, ui.update); // same + // + // example: + // Using return value for disconnect: + // | var link = dojo.connect(obj, "onchange", ui, "update"); + // | ... + // | dojo.disconnect(link); + // + // example: + // When onglobalevent executes, watcher.handler is invoked: + // | dojo.connect(null, "onglobalevent", watcher, "handler"); + // + // example: + // When ob.onCustomEvent executes, customEventHandler is invoked: + // | dojo.connect(ob, "onCustomEvent", null, "customEventHandler"); + // | dojo.connect(ob, "onCustomEvent", "customEventHandler"); // same + // + // example: + // When ob.onCustomEvent executes, customEventHandler is invoked + // with the same scope (this): + // | dojo.connect(ob, "onCustomEvent", null, customEventHandler); + // | dojo.connect(ob, "onCustomEvent", customEventHandler); // same + // + // example: + // When globalEvent executes, globalHandler is invoked + // with the same scope (this): + // | dojo.connect(null, "globalEvent", null, globalHandler); + // | dojo.connect("globalEvent", globalHandler); // same + + // normalize arguments + var a=arguments, args=[], i=0; + // if a[0] is a String, obj was ommited + args.push(dojo.isString(a[0]) ? null : a[i++], a[i++]); + // if the arg-after-next is a String or Function, context was NOT omitted + var a1 = a[i+1]; + args.push(dojo.isString(a1)||dojo.isFunction(a1) ? a[i++] : null, a[i++]); + // absorb any additional arguments + for(var l=a.length; i<l; i++){ args.push(a[i]); } + // do the actual work + return dojo._connect.apply(this, args); /*Handle*/ +} + +// used by non-browser hostenvs. always overriden by event.js +dojo._connect = function(obj, event, context, method){ + var l=dojo._listener, h=l.add(obj, event, dojo.hitch(context, method)); + return [obj, event, h, l]; // Handle +} + +dojo.disconnect = function(/*Handle*/ handle){ + // summary: + // Remove a link created by dojo.connect. + // description: + // Removes the connection between event and the method referenced by handle. + // handle: + // the return value of the dojo.connect call that created the connection. + if(handle && handle[0] !== undefined){ + dojo._disconnect.apply(this, handle); + // let's not keep this reference + delete handle[0]; + } +} + +dojo._disconnect = function(obj, event, handle, listener){ + listener.remove(obj, event, handle); +} + +// topic publish/subscribe + +dojo._topics = {}; + +dojo.subscribe = function(/*String*/ topic, /*Object|null*/ context, /*String|Function*/ method){ + // summary: + // Attach a listener to a named topic. The listener function is invoked whenever the + // named topic is published (see: dojo.publish). + // Returns a handle which is needed to unsubscribe this listener. + // context: + // Scope in which method will be invoked, or null for default scope. + // method: + // The name of a function in context, or a function reference. This is the function that + // is invoked when topic is published. + // example: + // | dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }); + // | dojo.publish("alerts", [ "read this", "hello world" ]); + + // support for 2 argument invocation (omitting context) depends on hitch + return [topic, dojo._listener.add(dojo._topics, topic, dojo.hitch(context, method))]; /*Handle*/ +} + +dojo.unsubscribe = function(/*Handle*/ handle){ + // summary: + // Remove a topic listener. + // handle: + // The handle returned from a call to subscribe. + // example: + // | var alerter = dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }; + // | ... + // | dojo.unsubscribe(alerter); + if(handle){ + dojo._listener.remove(dojo._topics, handle[0], handle[1]); + } +} + +dojo.publish = function(/*String*/ topic, /*Array*/ args){ + // summary: + // Invoke all listener method subscribed to topic. + // topic: + // The name of the topic to publish. + // args: + // An array of arguments. The arguments will be applied + // to each topic subscriber (as first class parameters, via apply). + // example: + // | dojo.subscribe("alerts", null, function(caption, message){ alert(caption + "\n" + message); }; + // | dojo.publish("alerts", [ "read this", "hello world" ]); + + // Note that args is an array, which is more efficient vs variable length + // argument list. Ideally, var args would be implemented via Array + // throughout the APIs. + var f = dojo._topics[topic]; + if(f){ + f.apply(this, args||[]); + } +} + +dojo.connectPublisher = function( /*String*/ topic, + /*Object|null*/ obj, + /*String*/ event){ + // summary: + // Ensure that everytime obj.event() is called, a message is published + // on the topic. Returns a handle which can be passed to + // dojo.disconnect() to disable subsequent automatic publication on + // the topic. + // topic: + // The name of the topic to publish. + // obj: + // The source object for the event function. Defaults to dojo.global + // if null. + // event: + // The name of the event function in obj. + // I.e. identifies a property obj[event]. + // example: + // | dojo.connectPublisher("/ajax/start", dojo, "xhrGet"); + var pf = function(){ dojo.publish(topic, arguments); } + return (event) ? dojo.connect(obj, event, pf) : dojo.connect(obj, pf); //Handle +}; + +} + +if(!dojo._hasResource["dojo._base.Deferred"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.Deferred"] = true; +dojo.provide("dojo._base.Deferred"); + + +dojo.Deferred = function(/*Function?*/ canceller){ + // summary: + // Encapsulates a sequence of callbacks in response to a value that + // may not yet be available. This is modeled after the Deferred class + // from Twisted <http://twistedmatrix.com>. + // description: + // JavaScript has no threads, and even if it did, threads are hard. + // Deferreds are a way of abstracting non-blocking events, such as the + // final response to an XMLHttpRequest. Deferreds create a promise to + // return a response a some point in the future and an easy way to + // register your interest in receiving that response. + // + // The most important methods for Deffered users are: + // + // * addCallback(handler) + // * addErrback(handler) + // * callback(result) + // * errback(result) + // + // In general, when a function returns a Deferred, users then "fill + // in" the second half of the contract by registering callbacks and + // error handlers. You may register as many callback and errback + // handlers as you like and they will be executed in the order + // registered when a result is provided. Usually this result is + // provided as the result of an asynchronous operation. The code + // "managing" the Deferred (the code that made the promise to provide + // an answer later) will use the callback() and errback() methods to + // communicate with registered listeners about the result of the + // operation. At this time, all registered result handlers are called + // *with the most recent result value*. + // + // Deferred callback handlers are treated as a chain, and each item in + // the chain is required to return a value that will be fed into + // successive handlers. The most minimal callback may be registered + // like this: + // + // | var d = new dojo.Deferred(); + // | d.addCallback(function(result){ return result; }); + // + // Perhaps the most common mistake when first using Deferreds is to + // forget to return a value (in most cases, the value you were + // passed). + // + // The sequence of callbacks is internally represented as a list of + // 2-tuples containing the callback/errback pair. For example, the + // following call sequence: + // + // | var d = new dojo.Deferred(); + // | d.addCallback(myCallback); + // | d.addErrback(myErrback); + // | d.addBoth(myBoth); + // | d.addCallbacks(myCallback, myErrback); + // + // is translated into a Deferred with the following internal + // representation: + // + // | [ + // | [myCallback, null], + // | [null, myErrback], + // | [myBoth, myBoth], + // | [myCallback, myErrback] + // | ] + // + // The Deferred also keeps track of its current status (fired). Its + // status may be one of three things: + // + // * -1: no value yet (initial condition) + // * 0: success + // * 1: error + // + // A Deferred will be in the error state if one of the following three + // conditions are met: + // + // 1. The result given to callback or errback is "instanceof" Error + // 2. The previous callback or errback raised an exception while + // executing + // 3. The previous callback or errback returned a value + // "instanceof" Error + // + // Otherwise, the Deferred will be in the success state. The state of + // the Deferred determines the next element in the callback sequence + // to run. + // + // When a callback or errback occurs with the example deferred chain, + // something equivalent to the following will happen (imagine + // that exceptions are caught and returned): + // + // | // d.callback(result) or d.errback(result) + // | if(!(result instanceof Error)){ + // | result = myCallback(result); + // | } + // | if(result instanceof Error){ + // | result = myErrback(result); + // | } + // | result = myBoth(result); + // | if(result instanceof Error){ + // | result = myErrback(result); + // | }else{ + // | result = myCallback(result); + // | } + // + // The result is then stored away in case another step is added to the + // callback sequence. Since the Deferred already has a value + // available, any new callbacks added will be called immediately. + // + // There are two other "advanced" details about this implementation + // that are useful: + // + // Callbacks are allowed to return Deferred instances themselves, so + // you can build complicated sequences of events with ease. + // + // The creator of the Deferred may specify a canceller. The canceller + // is a function that will be called if Deferred.cancel is called + // before the Deferred fires. You can use this to implement clean + // aborting of an XMLHttpRequest, etc. Note that cancel will fire the + // deferred with a CancelledError (unless your canceller returns + // another kind of error), so the errbacks should be prepared to + // handle that error for cancellable Deferreds. + // example: + // | var deferred = new dojo.Deferred(); + // | setTimeout(function(){ deferred.callback({success: true}); }, 1000); + // | return deferred; + // example: + // Deferred objects are often used when making code asynchronous. It + // may be easiest to write functions in a synchronous manner and then + // split code using a deferred to trigger a response to a long-lived + // operation. For example, instead of register a callback function to + // denote when a rendering operation completes, the function can + // simply return a deferred: + // + // | // callback style: + // | function renderLotsOfData(data, callback){ + // | var success = false + // | try{ + // | for(var x in data){ + // | renderDataitem(data[x]); + // | } + // | success = true; + // | }catch(e){ } + // | if(callback){ + // | callback(success); + // | } + // | } + // + // | // using callback style + // | renderLotsOfData(someDataObj, function(success){ + // | // handles success or failure + // | if(!success){ + // | promptUserToRecover(); + // | } + // | }); + // | // NOTE: no way to add another callback here!! + // example: + // Using a Deferred doesn't simplify the sending code any, but it + // provides a standard interface for callers and senders alike, + // providing both with a simple way to service multiple callbacks for + // an operation and freeing both sides from worrying about details + // such as "did this get called already?". With Deferreds, new + // callbacks can be added at any time. + // + // | // Deferred style: + // | function renderLotsOfData(data){ + // | var d = new dojo.Deferred(); + // | try{ + // | for(var x in data){ + // | renderDataitem(data[x]); + // | } + // | d.callback(true); + // | }catch(e){ + // | d.errback(new Error("rendering failed")); + // | } + // | return d; + // | } + // + // | // using Deferred style + // | renderLotsOfData(someDataObj).addErrback(function(){ + // | promptUserToRecover(); + // | }); + // | // NOTE: addErrback and addCallback both return the Deferred + // | // again, so we could chain adding callbacks or save the + // | // deferred for later should we need to be notified again. + // example: + // In this example, renderLotsOfData is syncrhonous and so both + // versions are pretty artificial. Putting the data display on a + // timeout helps show why Deferreds rock: + // + // | // Deferred style and async func + // | function renderLotsOfData(data){ + // | var d = new dojo.Deferred(); + // | setTimeout(function(){ + // | try{ + // | for(var x in data){ + // | renderDataitem(data[x]); + // | } + // | d.callback(true); + // | }catch(e){ + // | d.errback(new Error("rendering failed")); + // | } + // | }, 100); + // | return d; + // | } + // + // | // using Deferred style + // | renderLotsOfData(someDataObj).addErrback(function(){ + // | promptUserToRecover(); + // | }); + // + // Note that the caller doesn't have to change his code at all to + // handle the asynchronous case. + + this.chain = []; + this.id = this._nextId(); + this.fired = -1; + this.paused = 0; + this.results = [null, null]; + this.canceller = canceller; + this.silentlyCancelled = false; +}; + +dojo.extend(dojo.Deferred, { + /* + makeCalled: function(){ + // summary: + // returns a new, empty deferred, which is already in the called + // state. Calling callback() or errback() on this deferred will + // yeild an error and adding new handlers to it will result in + // them being called immediately. + var deferred = new dojo.Deferred(); + deferred.callback(); + return deferred; + }, + + toString: function(){ + var state; + if(this.fired == -1){ + state = 'unfired'; + }else{ + state = this.fired ? 'success' : 'error'; + } + return 'Deferred(' + this.id + ', ' + state + ')'; + }, + */ + + _nextId: (function(){ + var n = 1; + return function(){ return n++; }; + })(), + + cancel: function(){ + // summary: + // Cancels a Deferred that has not yet received a value, or is + // waiting on another Deferred as its value. + // description: + // If a canceller is defined, the canceller is called. If the + // canceller did not return an error, or there was no canceller, + // then the errback chain is started. + var err; + if(this.fired == -1){ + if(this.canceller){ + err = this.canceller(this); + }else{ + this.silentlyCancelled = true; + } + if(this.fired == -1){ + if(!(err instanceof Error)){ + var res = err; + var msg = "Deferred Cancelled"; + if(err && err.toString){ + msg += ": " + err.toString(); + } + err = new Error(msg); + err.dojoType = "cancel"; + err.cancelResult = res; + } + this.errback(err); + } + }else if( (this.fired == 0) && + (this.results[0] instanceof dojo.Deferred) + ){ + this.results[0].cancel(); + } + }, + + + _resback: function(res){ + // summary: + // The private primitive that means either callback or errback + this.fired = ((res instanceof Error) ? 1 : 0); + this.results[this.fired] = res; + this._fire(); + }, + + _check: function(){ + if(this.fired != -1){ + if(!this.silentlyCancelled){ + throw new Error("already called!"); + } + this.silentlyCancelled = false; + return; + } + }, + + callback: function(res){ + // summary: + // Begin the callback sequence with a non-error value. + + /* + callback or errback should only be called once on a given + Deferred. + */ + this._check(); + this._resback(res); + }, + + errback: function(/*Error*/res){ + // summary: + // Begin the callback sequence with an error result. + this._check(); + if(!(res instanceof Error)){ + res = new Error(res); + } + this._resback(res); + }, + + addBoth: function(/*Function|Object*/cb, /*String?*/cbfn){ + // summary: + // Add the same function as both a callback and an errback as the + // next element on the callback sequence.This is useful for code + // that you want to guarantee to run, e.g. a finalizer. + var enclosed = dojo.hitch.apply(dojo, arguments); + return this.addCallbacks(enclosed, enclosed); // dojo.Deferred + }, + + addCallback: function(/*Function|Object*/cb, /*String?*/cbfn /*...*/){ + // summary: + // Add a single callback to the end of the callback sequence. + return this.addCallbacks(dojo.hitch.apply(dojo, arguments)); // dojo.Deferred + }, + + addErrback: function(cb, cbfn){ + // summary: + // Add a single callback to the end of the callback sequence. + return this.addCallbacks(null, dojo.hitch.apply(dojo, arguments)); // dojo.Deferred + }, + + addCallbacks: function(cb, eb){ + // summary: + // Add separate callback and errback to the end of the callback + // sequence. + this.chain.push([cb, eb]) + if(this.fired >= 0){ + this._fire(); + } + return this; // dojo.Deferred + }, + + _fire: function(){ + // summary: + // Used internally to exhaust the callback sequence when a result + // is available. + var chain = this.chain; + var fired = this.fired; + var res = this.results[fired]; + var self = this; + var cb = null; + while( + (chain.length > 0) && + (this.paused == 0) + ){ + // Array + var f = chain.shift()[fired]; + if(!f){ continue; } + var func = function(){ + var ret = f(res); + //If no response, then use previous response. + if(typeof ret != "undefined"){ + res = ret; + } + fired = ((res instanceof Error) ? 1 : 0); + if(res instanceof dojo.Deferred){ + cb = function(res){ + self._resback(res); + // inlined from _pause() + self.paused--; + if( + (self.paused == 0) && + (self.fired >= 0) + ){ + self._fire(); + } + } + // inlined from _unpause + this.paused++; + } + }; + if(dojo.config.debugAtAllCosts){ + func.call(this); + }else{ + try{ + func.call(this); + }catch(err){ + fired = 1; + res = err; + } + } + } + this.fired = fired; + this.results[fired] = res; + if((cb)&&(this.paused)){ + // this is for "tail recursion" in case the dependent + // deferred is already fired + res.addBoth(cb); + } + } +}); + +} + +if(!dojo._hasResource["dojo._base.json"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.json"] = true; +dojo.provide("dojo._base.json"); + +dojo.fromJson = function(/*String*/ json){ + // summary: + // Parses a [JSON](http://json.org) string to return a JavaScript object. Throws for invalid JSON strings. + // json: + // a string literal of a JSON item, for instance: + // `'{ "foo": [ "bar", 1, { "baz": "thud" } ] }'` + + return eval("(" + json + ")"); // Object +} + +dojo._escapeString = function(/*String*/str){ + //summary: + // Adds escape sequences for non-visual characters, double quote and + // backslash and surrounds with double quotes to form a valid string + // literal. + return ('"' + str.replace(/(["\\])/g, '\\$1') + '"'). + replace(/[\f]/g, "\\f").replace(/[\b]/g, "\\b").replace(/[\n]/g, "\\n"). + replace(/[\t]/g, "\\t").replace(/[\r]/g, "\\r"); // string +} + +dojo.toJsonIndentStr = "\t"; +dojo.toJson = function(/*Object*/ it, /*Boolean?*/ prettyPrint, /*String?*/ _indentStr){ + // summary: + // Returns a [JSON](http://json.org) serialization of an object. + // + // description: + // Returns a [JSON](http://json.org) serialization of an object. + // Note that this doesn't check for infinite recursion, so don't do that! + // + // it: + // an object to be serialized. Objects may define their own + // serialization via a special "__json__" or "json" function + // property. If a specialized serializer has been defined, it will + // be used as a fallback. + // + // prettyPrint: + // if true, we indent objects and arrays to make the output prettier. + // The variable dojo.toJsonIndentStr is used as the indent string + // -- to use something other than the default (tab), + // change that variable before calling dojo.toJson(). + // + // _indentStr: + // private variable for recursive calls when pretty printing, do not use. + + if(it === undefined){ + return "undefined"; + } + var objtype = typeof it; + if(objtype == "number" || objtype == "boolean"){ + return it + ""; + } + if(it === null){ + return "null"; + } + if(dojo.isString(it)){ + return dojo._escapeString(it); + } + // recurse + var recurse = arguments.callee; + // short-circuit for objects that support "json" serialization + // if they return "self" then just pass-through... + var newObj; + _indentStr = _indentStr || ""; + var nextIndent = prettyPrint ? _indentStr + dojo.toJsonIndentStr : ""; + var tf = it.__json__||it.json; + if(dojo.isFunction(tf)){ + newObj = tf.call(it); + if(it !== newObj){ + return recurse(newObj, prettyPrint, nextIndent); + } + } + if(it.nodeType && it.cloneNode){ // isNode + // we can't seriailize DOM nodes as regular objects because they have cycles + // DOM nodes could be serialized with something like outerHTML, but + // that can be provided by users in the form of .json or .__json__ function. + throw new Error("Can't serialize DOM nodes"); + } + + var sep = prettyPrint ? " " : ""; + var newLine = prettyPrint ? "\n" : ""; + + // array + if(dojo.isArray(it)){ + var res = dojo.map(it, function(obj){ + var val = recurse(obj, prettyPrint, nextIndent); + if(typeof val != "string"){ + val = "undefined"; + } + return newLine + nextIndent + val; + }); + return "[" + res.join("," + sep) + newLine + _indentStr + "]"; + } + /* + // look in the registry + try { + window.o = it; + newObj = dojo.json.jsonRegistry.match(it); + return recurse(newObj, prettyPrint, nextIndent); + }catch(e){ + // + } + // it's a function with no adapter, skip it + */ + if(objtype == "function"){ + return null; // null + } + // generic object code path + var output = [], key; + for(key in it){ + var keyStr, val; + if(typeof key == "number"){ + keyStr = '"' + key + '"'; + }else if(typeof key == "string"){ + keyStr = dojo._escapeString(key); + }else{ + // skip non-string or number keys + continue; + } + val = recurse(it[key], prettyPrint, nextIndent); + if(typeof val != "string"){ + // skip non-serializable values + continue; + } + // FIXME: use += on Moz!! + // MOW NOTE: using += is a pain because you have to account for the dangling comma... + output.push(newLine + nextIndent + keyStr + ":" + sep + val); + } + return "{" + output.join("," + sep) + newLine + _indentStr + "}"; // String +} + +} + +if(!dojo._hasResource["dojo._base.array"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.array"] = true; + +dojo.provide("dojo._base.array"); + +(function(){ + var _getParts = function(arr, obj, cb){ + return [ + dojo.isString(arr) ? arr.split("") : arr, + obj || dojo.global, + // FIXME: cache the anonymous functions we create here? + dojo.isString(cb) ? new Function("item", "index", "array", cb) : cb + ]; + }; + + dojo.mixin(dojo, { + indexOf: function( /*Array*/ array, + /*Object*/ value, + /*Integer?*/ fromIndex, + /*Boolean?*/ findLast){ + // summary: + // locates the first index of the provided value in the + // passed array. If the value is not found, -1 is returned. + // description: + // For details on this method, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:indexOf + + var step = 1, end = array.length || 0, i = 0; + if(findLast){ + i = end - 1; + step = end = -1; + } + if(fromIndex != undefined){ i = fromIndex; } + if((findLast && i > end) || i < end){ + for(; i != end; i += step){ + if(array[i] == value){ return i; } + } + } + return -1; // Number + }, + + lastIndexOf: function(/*Array*/array, /*Object*/value, /*Integer?*/fromIndex){ + // summary: + // locates the last index of the provided value in the passed + // array. If the value is not found, -1 is returned. + // description: + // For details on this method, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:lastIndexOf + return dojo.indexOf(array, value, fromIndex, true); // Number + }, + + forEach: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ + // summary: + // for every item in arr, callback is invoked. Return values are ignored. + // arr: + // the array to iterate over. If a string, operates on individual characters. + // callback: + // a function is invoked with three arguments: item, index, and array + // thisObject: + // may be used to scope the call to callback + // description: + // This function corresponds to the JavaScript 1.6 + // Array.forEach() method. For more details, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:forEach + // example: + // | // log out all members of the array: + // | dojo.forEach( + // | [ "thinger", "blah", "howdy", 10 ], + // | function(item){ + // | + // | } + // | ); + // example: + // | // log out the members and their indexes + // | dojo.forEach( + // | [ "thinger", "blah", "howdy", 10 ], + // | function(item, idx, arr){ + // | + // | } + // | ); + // example: + // | // use a scoped object member as the callback + // | + // | var obj = { + // | prefix: "logged via obj.callback:", + // | callback: function(item){ + // | + // | } + // | }; + // | + // | // specifying the scope function executes the callback in that scope + // | dojo.forEach( + // | [ "thinger", "blah", "howdy", 10 ], + // | obj.callback, + // | obj + // | ); + // | + // | // alternately, we can accomplish the same thing with dojo.hitch() + // | dojo.forEach( + // | [ "thinger", "blah", "howdy", 10 ], + // | dojo.hitch(obj, "callback") + // | ); + + // match the behavior of the built-in forEach WRT empty arrs + if(!arr || !arr.length){ return; } + + // FIXME: there are several ways of handilng thisObject. Is + // dojo.global always the default context? + var _p = _getParts(arr, thisObject, callback); arr = _p[0]; + for(var i=0,l=arr.length; i<l; ++i){ + _p[2].call(_p[1], arr[i], i, arr); + } + }, + + _everyOrSome: function(/*Boolean*/every, /*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ + var _p = _getParts(arr, thisObject, callback); arr = _p[0]; + for(var i=0,l=arr.length; i<l; ++i){ + var result = !!_p[2].call(_p[1], arr[i], i, arr); + if(every ^ result){ + return result; // Boolean + } + } + return every; // Boolean + }, + + every: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ + // summary: + // Determines whether or not every item in arr satisfies the + // condition implemented by callback. + // arr: + // the array to iterate on. If a string, operates on individual characters. + // callback: + // a function is invoked with three arguments: item, index, + // and array and returns true if the condition is met. + // thisObject: + // may be used to scope the call to callback + // description: + // This function corresponds to the JavaScript 1.6 + // Array.every() method. For more details, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:every + // example: + // | // returns false + // | dojo.every([1, 2, 3, 4], function(item){ return item>1; }); + // example: + // | // returns true + // | dojo.every([1, 2, 3, 4], function(item){ return item>0; }); + return this._everyOrSome(true, arr, callback, thisObject); // Boolean + }, + + some: function(/*Array|String*/arr, /*Function|String*/callback, /*Object?*/thisObject){ + // summary: + // Determines whether or not any item in arr satisfies the + // condition implemented by callback. + // arr: + // the array to iterate over. If a string, operates on individual characters. + // callback: + // a function is invoked with three arguments: item, index, + // and array and returns true if the condition is met. + // thisObject: + // may be used to scope the call to callback + // description: + // This function corresponds to the JavaScript 1.6 + // Array.some() method. For more details, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:some + // example: + // | // is true + // | dojo.some([1, 2, 3, 4], function(item){ return item>1; }); + // example: + // | // is false + // | dojo.some([1, 2, 3, 4], function(item){ return item<1; }); + return this._everyOrSome(false, arr, callback, thisObject); // Boolean + }, + + map: function(/*Array|String*/arr, /*Function|String*/callback, /*Function?*/thisObject){ + // summary: + // applies callback to each element of arr and returns + // an Array with the results + // arr: + // the array to iterate on. If a string, operates on + // individual characters. + // callback: + // a function is invoked with three arguments, (item, index, + // array), and returns a value + // thisObject: + // may be used to scope the call to callback + // description: + // This function corresponds to the JavaScript 1.6 Array.map() + // method. For more details, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:map + // example: + // | // returns [2, 3, 4, 5] + // | dojo.map([1, 2, 3, 4], function(item){ return item+1 }); + + var _p = _getParts(arr, thisObject, callback); arr = _p[0]; + var outArr = (arguments[3] ? (new arguments[3]()) : []); + for(var i=0,l=arr.length; i<l; ++i){ + outArr.push(_p[2].call(_p[1], arr[i], i, arr)); + } + return outArr; // Array + }, + + filter: function(/*Array*/arr, /*Function|String*/callback, /*Object?*/thisObject){ + // summary: + // Returns a new Array with those items from arr that match the + // condition implemented by callback. + // arr: + // the array to iterate over. + // callback: + // a function that is invoked with three arguments (item, + // index, array). The return of this function is expected to + // be a boolean which determines whether the passed-in item + // will be included in the returned array. + // thisObject: + // may be used to scope the call to callback + // description: + // This function corresponds to the JavaScript 1.6 + // Array.filter() method. For more details, see: + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:filter + // example: + // | // returns [2, 3, 4] + // | dojo.filter([1, 2, 3, 4], function(item){ return item>1; }); + + var _p = _getParts(arr, thisObject, callback); arr = _p[0]; + var outArr = []; + for(var i=0,l=arr.length; i<l; ++i){ + if(_p[2].call(_p[1], arr[i], i, arr)){ + outArr.push(arr[i]); + } + } + return outArr; // Array + } + }); +})(); +/* +*/ + +} + +if(!dojo._hasResource["dojo._base.Color"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.Color"] = true; +dojo.provide("dojo._base.Color"); + + + +(function(){ + + var d = dojo; + + dojo.Color = function(/*Array|String|Object*/ color){ + // summary: + // Takes a named string, hex string, array of rgb or rgba values, + // an object with r, g, b, and a properties, or another `dojo.Color` object + // and creates a new Color instance to work from. + // + // example: + // Work with a Color instance: + // | var c = new dojo.Color(); + // | c.setColor([0,0,0]); // black + // | var hex = c.toHex(); // #000000 + // + // example: + // Work with a node's color: + // | var color = dojo.style("someNode", "backgroundColor"); + // | var n = new dojo.Color(color); + // | // adjust the color some + // | n.r *= .5; + // | // rgb(128, 255, 255); + if(color){ this.setColor(color); } + }; + + // FIXME: there's got to be a more space-efficient way to encode or discover these!! Use hex? + dojo.Color.named = { + black: [0,0,0], + silver: [192,192,192], + gray: [128,128,128], + white: [255,255,255], + maroon: [128,0,0], + red: [255,0,0], + purple: [128,0,128], + fuchsia: [255,0,255], + green: [0,128,0], + lime: [0,255,0], + olive: [128,128,0], + yellow: [255,255,0], + navy: [0,0,128], + blue: [0,0,255], + teal: [0,128,128], + aqua: [0,255,255] + }; + + dojo.extend(dojo.Color, { + r: 255, g: 255, b: 255, a: 1, + _set: function(r, g, b, a){ + var t = this; t.r = r; t.g = g; t.b = b; t.a = a; + }, + setColor: function(/*Array|String|Object*/ color){ + // summary: + // Takes a named string, hex string, array of rgb or rgba values, + // an object with r, g, b, and a properties, or another `dojo.Color` object + // and sets this color instance to that value. + // + // example: + // | var c = new dojo.Color(); // no color + // | c.setColor("#ededed"); // greyish + if(d.isString(color)){ + d.colorFromString(color, this); + }else if(d.isArray(color)){ + d.colorFromArray(color, this); + }else{ + this._set(color.r, color.g, color.b, color.a); + if(!(color instanceof d.Color)){ this.sanitize(); } + } + return this; // dojo.Color + }, + sanitize: function(){ + // summary: + // makes sure that the object has correct attributes + // description: + // the default implementation does nothing, include dojo.colors to + // augment it to real checks + return this; // dojo.Color + }, + toRgb: function(){ + // summary: Returns 3 component array of rgb values + // + // example: + // | var c = new dojo.Color("#000000"); + // | // [0,0,0] + var t = this; + return [t.r, t.g, t.b]; // Array + }, + toRgba: function(){ + // summary: Returns a 4 component array of rgba values + var t = this; + return [t.r, t.g, t.b, t.a]; // Array + }, + toHex: function(){ + // summary: Returns a css color string in hexadecimal representation + // + // example: + // | // #000000 + var arr = d.map(["r", "g", "b"], function(x){ + var s = this[x].toString(16); + return s.length < 2 ? "0" + s : s; + }, this); + return "#" + arr.join(""); // String + }, + toCss: function(/*Boolean?*/ includeAlpha){ + // summary: Returns a css color string in rgb(a) representation + // + // example: + // | var c = new dojo.Color("#FFF").toCss(); + // | // rgb('255','255','255') + var t = this, rgb = t.r + ", " + t.g + ", " + t.b; + return (includeAlpha ? "rgba(" + rgb + ", " + t.a : "rgb(" + rgb) + ")"; // String + }, + toString: function(){ + // summary: Returns a visual representation of the color + return this.toCss(true); // String + } + }); + + dojo.blendColors = function( + /*dojo.Color*/ start, + /*dojo.Color*/ end, + /*Number*/ weight, + /*dojo.Color?*/ obj + ){ + // summary: + // Blend colors end and start with weight from 0 to 1, 0.5 being a 50/50 blend, + // can reuse a previously allocated dojo.Color object for the result + var t = obj || new d.Color(); + d.forEach(["r", "g", "b", "a"], function(x){ + t[x] = start[x] + (end[x] - start[x]) * weight; + if(x != "a"){ t[x] = Math.round(t[x]); } + }); + return t.sanitize(); // dojo.Color + }; + + dojo.colorFromRgb = function(/*String*/ color, /*dojo.Color?*/ obj){ + // summary: get rgb(a) array from css-style color declarations + var m = color.toLowerCase().match(/^rgba?\(([\s\.,0-9]+)\)/); + return m && dojo.colorFromArray(m[1].split(/\s*,\s*/), obj); // dojo.Color + }; + + dojo.colorFromHex = function(/*String*/ color, /*dojo.Color?*/ obj){ + // summary: converts a hex string with a '#' prefix to a color object. + // Supports 12-bit #rgb shorthand. + // + // example: + // | var thing = dojo.colorFromHex("#ededed"); // grey, longhand + // + // example: + // | var thing = dojo.colorFromHex("#000"); // black, shorthand + var t = obj || new d.Color(), + bits = (color.length == 4) ? 4 : 8, + mask = (1 << bits) - 1; + color = Number("0x" + color.substr(1)); + if(isNaN(color)){ + return null; // dojo.Color + } + d.forEach(["b", "g", "r"], function(x){ + var c = color & mask; + color >>= bits; + t[x] = bits == 4 ? 17 * c : c; + }); + t.a = 1; + return t; // dojo.Color + }; + + dojo.colorFromArray = function(/*Array*/ a, /*dojo.Color?*/ obj){ + // summary: builds a color from 1, 2, 3, or 4 element array + var t = obj || new d.Color(); + t._set(Number(a[0]), Number(a[1]), Number(a[2]), Number(a[3])); + if(isNaN(t.a)){ t.a = 1; } + return t.sanitize(); // dojo.Color + }; + + dojo.colorFromString = function(/*String*/ str, /*dojo.Color?*/ obj){ + // summary: + // parses str for a color value. + // description: + // Acceptable input values for str may include arrays of any form + // accepted by dojo.colorFromArray, hex strings such as "#aaaaaa", or + // rgb or rgba strings such as "rgb(133, 200, 16)" or "rgba(10, 10, + // 10, 50)" + // returns: + // a dojo.Color object. If obj is passed, it will be the return value. + var a = d.Color.named[str]; + return a && d.colorFromArray(a, obj) || d.colorFromRgb(str, obj) || d.colorFromHex(str, obj); + }; + +})(); + +} + +if(!dojo._hasResource["dojo._base"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base"] = true; +dojo.provide("dojo._base"); + + + + + + + + + +} + +if(!dojo._hasResource["dojo._base.window"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.window"] = true; +dojo.provide("dojo._base.window"); + +/*===== +dojo.doc = { + // summary: + // Alias for the current document. 'dojo.doc' can be modified + // for temporary context shifting. Also see dojo.withDoc(). + // description: + // Refer to dojo.doc rather + // than referring to 'window.document' to ensure your code runs + // correctly in managed contexts. + // example: + // | n.appendChild(dojo.doc.createElement('div')); +} +=====*/ +dojo.doc = window["document"] || null; + +dojo.body = function(){ + // summary: + // Return the body element of the document + // return the body object associated with dojo.doc + // example: + // | dojo.body().appendChild(dojo.doc.createElement('div')); + + // Note: document.body is not defined for a strict xhtml document + // Would like to memoize this, but dojo.doc can change vi dojo.withDoc(). + return dojo.doc.body || dojo.doc.getElementsByTagName("body")[0]; // Node +} + +dojo.setContext = function(/*Object*/globalObject, /*DocumentElement*/globalDocument){ + // summary: + // changes the behavior of many core Dojo functions that deal with + // namespace and DOM lookup, changing them to work in a new global + // context (e.g., an iframe). The varibles dojo.global and dojo.doc + // are modified as a result of calling this function and the result of + // `dojo.body()` likewise differs. + dojo.global = globalObject; + dojo.doc = globalDocument; +}; + +dojo.withGlobal = function( /*Object*/globalObject, + /*Function*/callback, + /*Object?*/thisObject, + /*Array?*/cbArguments){ + // summary: + // Invoke callback with globalObject as dojo.global and + // globalObject.document as dojo.doc. + // description: + // Invoke callback with globalObject as dojo.global and + // globalObject.document as dojo.doc. If provided, globalObject + // will be executed in the context of object thisObject + // When callback() returns or throws an error, the dojo.global + // and dojo.doc will be restored to its previous state. + + var oldGlob = dojo.global; + try{ + dojo.global = globalObject; + return dojo.withDoc.call(null, globalObject.document, callback, thisObject, cbArguments); + }finally{ + dojo.global = oldGlob; + } +} + +dojo.withDoc = function( /*DocumentElement*/documentObject, + /*Function*/callback, + /*Object?*/thisObject, + /*Array?*/cbArguments){ + // summary: + // Invoke callback with documentObject as dojo.doc. + // description: + // Invoke callback with documentObject as dojo.doc. If provided, + // callback will be executed in the context of object thisObject + // When callback() returns or throws an error, the dojo.doc will + // be restored to its previous state. + + var oldDoc = dojo.doc, + oldLtr = dojo._bodyLtr; + + try{ + dojo.doc = documentObject; + delete dojo._bodyLtr; // uncache + + if(thisObject && dojo.isString(callback)){ + callback = thisObject[callback]; + } + + return callback.apply(thisObject, cbArguments || []); + }finally{ + dojo.doc = oldDoc; + if(oldLtr !== undefined){ dojo._bodyLtr = oldLtr; } + } +}; + + +} + +if(!dojo._hasResource["dojo._base.event"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.event"] = true; +dojo.provide("dojo._base.event"); + + +// this file courtesy of the TurboAjax Group, licensed under a Dojo CLA + +(function(){ + // DOM event listener machinery + var del = (dojo._event_listener = { + add: function(/*DOMNode*/node, /*String*/name, /*Function*/fp){ + if(!node){return;} + name = del._normalizeEventName(name); + fp = del._fixCallback(name, fp); + var oname = name; + if( + !dojo.isIE && + (name == "mouseenter" || name == "mouseleave") + ){ + var ofp = fp; + //oname = name; + name = (name == "mouseenter") ? "mouseover" : "mouseout"; + fp = function(e){ + if(dojo.isFF <= 2) { + // check tagName to fix a FF2 bug with invalid nodes (hidden child DIV of INPUT) + // which causes isDescendant to return false which causes + // spurious, and more importantly, incorrect mouse events to fire. + // TODO: remove tagName check when Firefox 2 is no longer supported + try{ e.relatedTarget.tagName; }catch(e2){ return; } + } + if(!dojo.isDescendant(e.relatedTarget, node)){ + // e.type = oname; // FIXME: doesn't take? SJM: event.type is generally immutable. + return ofp.call(this, e); + } + } + } + node.addEventListener(name, fp, false); + return fp; /*Handle*/ + }, + remove: function(/*DOMNode*/node, /*String*/event, /*Handle*/handle){ + // summary: + // clobbers the listener from the node + // node: + // DOM node to attach the event to + // event: + // the name of the handler to remove the function from + // handle: + // the handle returned from add + if(node){ + event = del._normalizeEventName(event); + if(!dojo.isIE && (event == "mouseenter" || event == "mouseleave")){ + event = (event == "mouseenter") ? "mouseover" : "mouseout"; + } + + node.removeEventListener(event, handle, false); + } + }, + _normalizeEventName: function(/*String*/name){ + // Generally, name should be lower case, unless it is special + // somehow (e.g. a Mozilla DOM event). + // Remove 'on'. + return name.slice(0,2) =="on" ? name.slice(2) : name; + }, + _fixCallback: function(/*String*/name, fp){ + // By default, we only invoke _fixEvent for 'keypress' + // If code is added to _fixEvent for other events, we have + // to revisit this optimization. + // This also applies to _fixEvent overrides for Safari and Opera + // below. + return name != "keypress" ? fp : function(e){ return fp.call(this, del._fixEvent(e, this)); }; + }, + _fixEvent: function(evt, sender){ + // _fixCallback only attaches us to keypress. + // Switch on evt.type anyway because we might + // be called directly from dojo.fixEvent. + switch(evt.type){ + case "keypress": + del._setKeyChar(evt); + break; + } + return evt; + }, + _setKeyChar: function(evt){ + evt.keyChar = evt.charCode ? String.fromCharCode(evt.charCode) : ''; + evt.charOrCode = evt.keyChar || evt.keyCode; + }, + // For IE and Safari: some ctrl-key combinations (mostly w/punctuation) do not emit a char code in IE + // we map those virtual key codes to ascii here + // not valid for all (non-US) keyboards, so maybe we shouldn't bother + _punctMap: { + 106:42, + 111:47, + 186:59, + 187:43, + 188:44, + 189:45, + 190:46, + 191:47, + 192:96, + 219:91, + 220:92, + 221:93, + 222:39 + } + }); + + // DOM events + + dojo.fixEvent = function(/*Event*/evt, /*DOMNode*/sender){ + // summary: + // normalizes properties on the event object including event + // bubbling methods, keystroke normalization, and x/y positions + // evt: Event + // native event object + // sender: DOMNode + // node to treat as "currentTarget" + return del._fixEvent(evt, sender); + } + + dojo.stopEvent = function(/*Event*/evt){ + // summary: + // prevents propagation and clobbers the default action of the + // passed event + // evt: Event + // The event object. If omitted, window.event is used on IE. + evt.preventDefault(); + evt.stopPropagation(); + // NOTE: below, this method is overridden for IE + } + + // the default listener to use on dontFix nodes, overriden for IE + var node_listener = dojo._listener; + + // Unify connect and event listeners + dojo._connect = function(obj, event, context, method, dontFix){ + // FIXME: need a more strict test + var isNode = obj && (obj.nodeType||obj.attachEvent||obj.addEventListener); + // choose one of three listener options: raw (connect.js), DOM event on a Node, custom event on a Node + // we need the third option to provide leak prevention on broken browsers (IE) + var lid = isNode ? (dontFix ? 2 : 1) : 0, l = [dojo._listener, del, node_listener][lid]; + // create a listener + var h = l.add(obj, event, dojo.hitch(context, method)); + // formerly, the disconnect package contained "l" directly, but if client code + // leaks the disconnect package (by connecting it to a node), referencing "l" + // compounds the problem. + // instead we return a listener id, which requires custom _disconnect below. + // return disconnect package + return [ obj, event, h, lid ]; + } + + dojo._disconnect = function(obj, event, handle, listener){ + ([dojo._listener, del, node_listener][listener]).remove(obj, event, handle); + } + + // Constants + + // Public: client code should test + // keyCode against these named constants, as the + // actual codes can vary by browser. + dojo.keys = { + // summary: definitions for common key values + BACKSPACE: 8, + TAB: 9, + CLEAR: 12, + ENTER: 13, + SHIFT: 16, + CTRL: 17, + ALT: 18, + PAUSE: 19, + CAPS_LOCK: 20, + ESCAPE: 27, + SPACE: 32, + PAGE_UP: 33, + PAGE_DOWN: 34, + END: 35, + HOME: 36, + LEFT_ARROW: 37, + UP_ARROW: 38, + RIGHT_ARROW: 39, + DOWN_ARROW: 40, + INSERT: 45, + DELETE: 46, + HELP: 47, + LEFT_WINDOW: 91, + RIGHT_WINDOW: 92, + SELECT: 93, + NUMPAD_0: 96, + NUMPAD_1: 97, + NUMPAD_2: 98, + NUMPAD_3: 99, + NUMPAD_4: 100, + NUMPAD_5: 101, + NUMPAD_6: 102, + NUMPAD_7: 103, + NUMPAD_8: 104, + NUMPAD_9: 105, + NUMPAD_MULTIPLY: 106, + NUMPAD_PLUS: 107, + NUMPAD_ENTER: 108, + NUMPAD_MINUS: 109, + NUMPAD_PERIOD: 110, + NUMPAD_DIVIDE: 111, + F1: 112, + F2: 113, + F3: 114, + F4: 115, + F5: 116, + F6: 117, + F7: 118, + F8: 119, + F9: 120, + F10: 121, + F11: 122, + F12: 123, + F13: 124, + F14: 125, + F15: 126, + NUM_LOCK: 144, + SCROLL_LOCK: 145 + }; + + // IE event normalization + if(dojo.isIE){ + var _trySetKeyCode = function(e, code){ + try{ + // squelch errors when keyCode is read-only + // (e.g. if keyCode is ctrl or shift) + return (e.keyCode = code); + }catch(e){ + return 0; + } + } + + // by default, use the standard listener + var iel = dojo._listener; + var listenersName = (dojo._ieListenersName = "_" + dojo._scopeName + "_listeners"); + // dispatcher tracking property + if(!dojo.config._allow_leaks){ + // custom listener that handles leak protection for DOM events + node_listener = iel = dojo._ie_listener = { + // support handler indirection: event handler functions are + // referenced here. Event dispatchers hold only indices. + handlers: [], + // add a listener to an object + add: function(/*Object*/ source, /*String*/ method, /*Function*/ listener){ + source = source || dojo.global; + var f = source[method]; + if(!f||!f[listenersName]){ + var d = dojo._getIeDispatcher(); + // original target function is special + d.target = f && (ieh.push(f) - 1); + // dispatcher holds a list of indices into handlers table + d[listenersName] = []; + // redirect source to dispatcher + f = source[method] = d; + } + return f[listenersName].push(ieh.push(listener) - 1) ; /*Handle*/ + }, + // remove a listener from an object + remove: function(/*Object*/ source, /*String*/ method, /*Handle*/ handle){ + var f = (source||dojo.global)[method], l = f && f[listenersName]; + if(f && l && handle--){ + delete ieh[l[handle]]; + delete l[handle]; + } + } + }; + // alias used above + var ieh = iel.handlers; + } + + dojo.mixin(del, { + add: function(/*DOMNode*/node, /*String*/event, /*Function*/fp){ + if(!node){return;} // undefined + event = del._normalizeEventName(event); + if(event=="onkeypress"){ + // we need to listen to onkeydown to synthesize + // keypress events that otherwise won't fire + // on IE + var kd = node.onkeydown; + if(!kd || !kd[listenersName] || !kd._stealthKeydownHandle){ + var h = del.add(node, "onkeydown", del._stealthKeyDown); + kd = node.onkeydown; + kd._stealthKeydownHandle = h; + kd._stealthKeydownRefs = 1; + }else{ + kd._stealthKeydownRefs++; + } + } + return iel.add(node, event, del._fixCallback(fp)); + }, + remove: function(/*DOMNode*/node, /*String*/event, /*Handle*/handle){ + event = del._normalizeEventName(event); + iel.remove(node, event, handle); + if(event=="onkeypress"){ + var kd = node.onkeydown; + if(--kd._stealthKeydownRefs <= 0){ + iel.remove(node, "onkeydown", kd._stealthKeydownHandle); + delete kd._stealthKeydownHandle; + } + } + }, + _normalizeEventName: function(/*String*/eventName){ + // Generally, eventName should be lower case, unless it is + // special somehow (e.g. a Mozilla event) + // ensure 'on' + return eventName.slice(0,2) != "on" ? "on" + eventName : eventName; + }, + _nop: function(){}, + _fixEvent: function(/*Event*/evt, /*DOMNode*/sender){ + // summary: + // normalizes properties on the event object including event + // bubbling methods, keystroke normalization, and x/y positions + // evt: native event object + // sender: node to treat as "currentTarget" + if(!evt){ + var w = sender && (sender.ownerDocument || sender.document || sender).parentWindow || window; + evt = w.event; + } + if(!evt){return(evt);} + evt.target = evt.srcElement; + evt.currentTarget = (sender || evt.srcElement); + evt.layerX = evt.offsetX; + evt.layerY = evt.offsetY; + // FIXME: scroll position query is duped from dojo.html to + // avoid dependency on that entire module. Now that HTML is in + // Base, we should convert back to something similar there. + var se = evt.srcElement, doc = (se && se.ownerDocument) || document; + // DO NOT replace the following to use dojo.body(), in IE, document.documentElement should be used + // here rather than document.body + var docBody = ((dojo.isIE < 6) || (doc["compatMode"] == "BackCompat")) ? doc.body : doc.documentElement; + var offset = dojo._getIeDocumentElementOffset(); + evt.pageX = evt.clientX + dojo._fixIeBiDiScrollLeft(docBody.scrollLeft || 0) - offset.x; + evt.pageY = evt.clientY + (docBody.scrollTop || 0) - offset.y; + if(evt.type == "mouseover"){ + evt.relatedTarget = evt.fromElement; + } + if(evt.type == "mouseout"){ + evt.relatedTarget = evt.toElement; + } + evt.stopPropagation = del._stopPropagation; + evt.preventDefault = del._preventDefault; + return del._fixKeys(evt); + }, + _fixKeys: function(evt){ + switch(evt.type){ + case "keypress": + var c = ("charCode" in evt ? evt.charCode : evt.keyCode); + if (c==10){ + // CTRL-ENTER is CTRL-ASCII(10) on IE, but CTRL-ENTER on Mozilla + c=0; + evt.keyCode = 13; + }else if(c==13||c==27){ + c=0; // Mozilla considers ENTER and ESC non-printable + }else if(c==3){ + c=99; // Mozilla maps CTRL-BREAK to CTRL-c + } + // Mozilla sets keyCode to 0 when there is a charCode + // but that stops the event on IE. + evt.charCode = c; + del._setKeyChar(evt); + break; + } + return evt; + }, + _stealthKeyDown: function(evt){ + // IE doesn't fire keypress for most non-printable characters. + // other browsers do, we simulate it here. + var kp = evt.currentTarget.onkeypress; + // only works if kp exists and is a dispatcher + if(!kp || !kp[listenersName]){ return; } + // munge key/charCode + var k=evt.keyCode; + // These are Windows Virtual Key Codes + // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/WinUI/WindowsUserInterface/UserInput/VirtualKeyCodes.asp + var unprintable = k!=13 && k!=32 && k!=27 && (k<48||k>90) && (k<96||k>111) && (k<186||k>192) && (k<219||k>222); + // synthesize keypress for most unprintables and CTRL-keys + if(unprintable||evt.ctrlKey){ + var c = unprintable ? 0 : k; + if(evt.ctrlKey){ + if(k==3 || k==13){ + return; // IE will post CTRL-BREAK, CTRL-ENTER as keypress natively + }else if(c>95 && c<106){ + c -= 48; // map CTRL-[numpad 0-9] to ASCII + }else if((!evt.shiftKey)&&(c>=65&&c<=90)){ + c += 32; // map CTRL-[A-Z] to lowercase + }else{ + c = del._punctMap[c] || c; // map other problematic CTRL combinations to ASCII + } + } + // simulate a keypress event + var faux = del._synthesizeEvent(evt, {type: 'keypress', faux: true, charCode: c}); + kp.call(evt.currentTarget, faux); + evt.cancelBubble = faux.cancelBubble; + evt.returnValue = faux.returnValue; + _trySetKeyCode(evt, faux.keyCode); + } + }, + // Called in Event scope + _stopPropagation: function(){ + this.cancelBubble = true; + }, + _preventDefault: function(){ + // Setting keyCode to 0 is the only way to prevent certain keypresses (namely + // ctrl-combinations that correspond to menu accelerator keys). + // Otoh, it prevents upstream listeners from getting this information + // Try to split the difference here by clobbering keyCode only for ctrl + // combinations. If you still need to access the key upstream, bubbledKeyCode is + // provided as a workaround. + this.bubbledKeyCode = this.keyCode; + if(this.ctrlKey){_trySetKeyCode(this, 0);} + this.returnValue = false; + } + }); + + // override stopEvent for IE + dojo.stopEvent = function(evt){ + evt = evt || window.event; + del._stopPropagation.call(evt); + del._preventDefault.call(evt); + } + } + + del._synthesizeEvent = function(evt, props){ + var faux = dojo.mixin({}, evt, props); + del._setKeyChar(faux); + // FIXME: would prefer to use dojo.hitch: dojo.hitch(evt, evt.preventDefault); + // but it throws an error when preventDefault is invoked on Safari + // does Event.preventDefault not support "apply" on Safari? + faux.preventDefault = function(){ evt.preventDefault(); }; + faux.stopPropagation = function(){ evt.stopPropagation(); }; + return faux; + } + + // Opera event normalization + if(dojo.isOpera){ + dojo.mixin(del, { + _fixEvent: function(evt, sender){ + switch(evt.type){ + case "keypress": + var c = evt.which; + if(c==3){ + c=99; // Mozilla maps CTRL-BREAK to CTRL-c + } + // can't trap some keys at all, like INSERT and DELETE + // there is no differentiating info between DELETE and ".", or INSERT and "-" + c = c<41 && !evt.shiftKey ? 0 : c; + if(evt.ctrlKey && !evt.shiftKey && c>=65 && c<=90){ + // lowercase CTRL-[A-Z] keys + c += 32; + } + return del._synthesizeEvent(evt, { charCode: c }); + } + return evt; + } + }); + } + + // Webkit event normalization + if(dojo.isWebKit){ + del._add = del.add; + del._remove = del.remove; + + dojo.mixin(del, { + add: function(/*DOMNode*/node, /*String*/event, /*Function*/fp){ + if(!node){return;} // undefined + var handle = del._add(node, event, fp); + if(del._normalizeEventName(event) == "keypress"){ + // we need to listen to onkeydown to synthesize + // keypress events that otherwise won't fire + // in Safari 3.1+: https://lists.webkit.org/pipermail/webkit-dev/2007-December/002992.html + handle._stealthKeyDownHandle = del._add(node, "keydown", function(evt){ + //A variation on the IE _stealthKeydown function + //Synthesize an onkeypress event, but only for unprintable characters. + var k=evt.keyCode; + // These are Windows Virtual Key Codes + // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/WinUI/WindowsUserInterface/UserInput/VirtualKeyCodes.asp + var unprintable = k!=13 && k!=32 && k!=27 && (k<48 || k>90) && (k<96 || k>111) && (k<186 || k>192) && (k<219 || k>222); + // synthesize keypress for most unprintables and CTRL-keys + if(unprintable || evt.ctrlKey){ + var c = unprintable ? 0 : k; + if(evt.ctrlKey){ + if(k==3 || k==13){ + return; // IE will post CTRL-BREAK, CTRL-ENTER as keypress natively + }else if(c>95 && c<106){ + c -= 48; // map CTRL-[numpad 0-9] to ASCII + }else if(!evt.shiftKey && c>=65 && c<=90){ + c += 32; // map CTRL-[A-Z] to lowercase + }else{ + c = del._punctMap[c] || c; // map other problematic CTRL combinations to ASCII + } + } + // simulate a keypress event + var faux = del._synthesizeEvent(evt, {type: 'keypress', faux: true, charCode: c}); + fp.call(evt.currentTarget, faux); + } + }); + } + return handle; /*Handle*/ + }, + + remove: function(/*DOMNode*/node, /*String*/event, /*Handle*/handle){ + if(node){ + if(handle._stealthKeyDownHandle){ + del._remove(node, "keydown", handle._stealthKeyDownHandle); + } + del._remove(node, event, handle); + } + }, + _fixEvent: function(evt, sender){ + switch(evt.type){ + case "keypress": + if(evt.faux){ return evt; } + var c = evt.charCode; + c = c>=32 ? c : 0; + return del._synthesizeEvent(evt, {charCode: c, faux: true}); + } + return evt; + } + }); + } + })(); + +if(dojo.isIE){ + // keep this out of the closure + // closing over 'iel' or 'ieh' b0rks leak prevention + // ls[i] is an index into the master handler array + dojo._ieDispatcher = function(args, sender){ + var ap=Array.prototype, h=dojo._ie_listener.handlers, c=args.callee, ls=c[dojo._ieListenersName], t=h[c.target]; + // return value comes from original target function + var r = t && t.apply(sender, args); + // make local copy of listener array so it's immutable during processing + var lls = [].concat(ls); + // invoke listeners after target function + for(var i in lls){ + var f = h[lls[i]]; + if(!(i in ap) && f){ + f.apply(sender, args); + } + } + return r; + } + dojo._getIeDispatcher = function(){ + // ensure the returned function closes over nothing ("new Function" apparently doesn't close) + return new Function(dojo._scopeName + "._ieDispatcher(arguments, this)"); // function + } + // keep this out of the closure to reduce RAM allocation + dojo._event_listener._fixCallback = function(fp){ + var f = dojo._event_listener._fixEvent; + return function(e){ return fp.call(this, f(e, this)); }; + } +} + +} + +if(!dojo._hasResource["dojo._base.html"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.html"] = true; + +dojo.provide("dojo._base.html"); + +// FIXME: need to add unit tests for all the semi-public methods + +try{ + document.execCommand("BackgroundImageCache", false, true); +}catch(e){ + // sane browsers don't have cache "issues" +} + +// ============================= +// DOM Functions +// ============================= + +/*===== +dojo.byId = function(id, doc){ + // summary: + // Returns DOM node with matching `id` attribute or `null` + // if not found, similar to "$" function in another library. + // If `id` is a DomNode, this function is a no-op. + // + // id: String|DOMNode + // A string to match an HTML id attribute or a reference to a DOM Node + // + // doc: Document? + // Document to work in. Defaults to the current value of + // dojo.doc. Can be used to retrieve + // node references from other documents. + // + // example: + // Look up a node by ID: + // | var n = dojo.byId("foo"); + // + // example: + // Check if a node exists. + // | if(dojo.byId("bar")){ ... } + // + // example: + // Allow string or DomNode references to be passed to a custom function: + // | var foo = function(nodeOrId){ + // | nodeOrId = dojo.byId(nodeOrId); + // | // ... more stuff + // | } +=====*/ + +if(dojo.isIE || dojo.isOpera){ + dojo.byId = function(id, doc){ + if(dojo.isString(id)){ + var _d = doc || dojo.doc; + var te = _d.getElementById(id); + // attributes.id.value is better than just id in case the + // user has a name=id inside a form + if(te && (te.attributes.id.value == id || te.id == id)){ + return te; + }else{ + var eles = _d.all[id]; + if(!eles || eles.nodeName){ + eles = [eles]; + } + // if more than 1, choose first with the correct id + var i=0; + while((te=eles[i++])){ + if((te.attributes && te.attributes.id && te.attributes.id.value == id) + || te.id == id){ + return te; + } + } + } + }else{ + return id; // DomNode + } + }; +}else{ + dojo.byId = function(id, doc){ + return dojo.isString(id) ? (doc || dojo.doc).getElementById(id) : id; // DomNode + }; +} +/*===== +} +=====*/ + +(function(){ + var d = dojo; + + var _destroyContainer = null; + d.addOnWindowUnload(function(){ + _destroyContainer = null; //prevent IE leak + }); + +/*===== + dojo._destroyElement = function(node){ + // summary: Existing alias for `dojo.destroy`. Deprecated, will be removed in 2.0 + } +=====*/ + dojo._destroyElement = dojo.destroy = function(/*String|DomNode*/node){ + // summary: + // Removes a node from its parent, clobbering it and all of its + // children. + // + // description: + // Removes a node from its parent, clobbering it and all of its + // children. Function only works with DomNodes, and returns nothing. + // + // node: + // A String ID or DomNode reference of the element to be destroyed + // + // example: + // Destroy a node byId: + // | dojo.destroy("someId"); + // + // example: + // Destroy all nodes in a list by reference: + // | dojo.query(".someNode").forEach(dojo.destroy); + + node = d.byId(node); + try{ + if(!_destroyContainer || _destroyContainer.ownerDocument != node.ownerDocument){ + _destroyContainer = node.ownerDocument.createElement("div"); + } + _destroyContainer.appendChild(node.parentNode ? node.parentNode.removeChild(node) : node); + // NOTE: see http://trac.dojotoolkit.org/ticket/2931. This may be a bug and not a feature + _destroyContainer.innerHTML = ""; + }catch(e){ + /* squelch */ + } + }; + + dojo.isDescendant = function(/*DomNode|String*/node, /*DomNode|String*/ancestor){ + // summary: + // Returns true if node is a descendant of ancestor + // node: string id or node reference to test + // ancestor: string id or node reference of potential parent to test against + try{ + node = d.byId(node); + ancestor = d.byId(ancestor); + while(node){ + if(node === ancestor){ + return true; // Boolean + } + node = node.parentNode; + } + }catch(e){ /* squelch, return false */ } + return false; // Boolean + }; + + dojo.setSelectable = function(/*DomNode|String*/node, /*Boolean*/selectable){ + // summary: enable or disable selection on a node + // node: + // id or reference to node + // selectable: + // state to put the node in. false indicates unselectable, true + // allows selection. + node = d.byId(node); + if(d.isMozilla){ + node.style.MozUserSelect = selectable ? "" : "none"; + }else if(d.isKhtml || d.isWebKit){ + node.style.KhtmlUserSelect = selectable ? "auto" : "none"; + }else if(d.isIE){ + var v = (node.unselectable = selectable ? "" : "on"); + d.query("*", node).forEach("item.unselectable = '"+v+"'"); + } + //FIXME: else? Opera? + }; + + var _insertBefore = function(/*DomNode*/node, /*DomNode*/ref){ + var parent = ref.parentNode; + if(parent){ + parent.insertBefore(node, ref); + } + } + + var _insertAfter = function(/*DomNode*/node, /*DomNode*/ref){ + // summary: + // Try to insert node after ref + var parent = ref.parentNode; + if(parent){ + if(parent.lastChild == ref){ + parent.appendChild(node); + }else{ + parent.insertBefore(node, ref.nextSibling); + } + } + } + + dojo.place = function(node, refNode, position){ + // summary: + // Attempt to insert node into the DOM, choosing from various positioning options. + // Returns true if successful, false otherwise. + // + // node: String|DomNode + // id or node reference, or HTML fragment starting with "<" to place relative to refNode + // + // refNode: String|DomNode + // id or node reference to use as basis for placement + // + // position: String|Number? + // string noting the position of node relative to refNode or a + // number indicating the location in the childNodes collection of refNode. + // Accepted string values are: + // | * before + // | * after + // | * replace + // | * only + // | * first + // | * last + // "first" and "last" indicate positions as children of refNode, "replace" replaces refNode, + // "only" replaces all children. position defaults to "last" if not specified + // + // returns: DomNode + // Returned values is the first argument resolved to a DOM node. + // + // .place() is also a method of `dojo.NodeList`, allowing `dojo.query` node lookups. + // + // example: + // Place a node by string id as the last child of another node by string id: + // | dojo.place("someNode", "anotherNode"); + // + // example: + // Place a node by string id before another node by string id + // | dojo.place("someNode", "anotherNode", "before"); + // + // example: + // Create a Node, and place it in the body element (last child): + // | dojo.place(dojo.create('div'), dojo.body()); + // + // example: + // Put a new LI as the first child of a list by id: + // | dojo.place(dojo.create('li'), "someUl", "first"); + + refNode = d.byId(refNode); + if(d.isString(node)){ + node = node.charAt(0) == "<" ? d._toDom(node, refNode.ownerDocument) : d.byId(node); + } + if(typeof position == "number"){ + var cn = refNode.childNodes; + if(!cn.length || cn.length <= position){ + refNode.appendChild(node); + }else{ + _insertBefore(node, cn[position < 0 ? 0 : position]); + } + }else{ + switch(position){ + case "before": + _insertBefore(node, refNode); + break; + case "after": + _insertAfter(node, refNode); + break; + case "replace": + refNode.parentNode.replaceChild(node, refNode); + break; + case "only": + d.empty(refNode); + refNode.appendChild(node); + break; + case "first": + if(refNode.firstChild){ + _insertBefore(node, refNode.firstChild); + break; + } + // else fallthrough... + default: // aka: last + refNode.appendChild(node); + } + } + return node; // DomNode + } + + // Box functions will assume this model. + // On IE/Opera, BORDER_BOX will be set if the primary document is in quirks mode. + // Can be set to change behavior of box setters. + + // can be either: + // "border-box" + // "content-box" (default) + dojo.boxModel = "content-box"; + + // We punt per-node box mode testing completely. + // If anybody cares, we can provide an additional (optional) unit + // that overrides existing code to include per-node box sensitivity. + + // Opera documentation claims that Opera 9 uses border-box in BackCompat mode. + // but experiments (Opera 9.10.8679 on Windows Vista) indicate that it actually continues to use content-box. + // IIRC, earlier versions of Opera did in fact use border-box. + // Opera guys, this is really confusing. Opera being broken in quirks mode is not our fault. + + if(d.isIE /*|| dojo.isOpera*/){ + var _dcm = document.compatMode; + // client code may have to adjust if compatMode varies across iframes + d.boxModel = _dcm == "BackCompat" || _dcm == "QuirksMode" || d.isIE < 6 ? "border-box" : "content-box"; // FIXME: remove IE < 6 support? + } + + // ============================= + // Style Functions + // ============================= + + // getComputedStyle drives most of the style code. + // Wherever possible, reuse the returned object. + // + // API functions below that need to access computed styles accept an + // optional computedStyle parameter. + // If this parameter is omitted, the functions will call getComputedStyle themselves. + // This way, calling code can access computedStyle once, and then pass the reference to + // multiple API functions. + +/*===== + dojo.getComputedStyle = function(node){ + // summary: + // Returns a "computed style" object. + // + // description: + // Gets a "computed style" object which can be used to gather + // information about the current state of the rendered node. + // + // Note that this may behave differently on different browsers. + // Values may have different formats and value encodings across + // browsers. + // + // Note also that this method is expensive. Wherever possible, + // reuse the returned object. + // + // Use the dojo.style() method for more consistent (pixelized) + // return values. + // + // node: DOMNode + // A reference to a DOM node. Does NOT support taking an + // ID string for speed reasons. + // example: + // | dojo.getComputedStyle(dojo.byId('foo')).borderWidth; + // + // example: + // Reusing the returned object, avoiding multiple lookups: + // | var cs = dojo.getComputedStyle(dojo.byId("someNode")); + // | var w = cs.width, h = cs.height; + return; // CSS2Properties + } +=====*/ + + // Although we normally eschew argument validation at this + // level, here we test argument 'node' for (duck)type. + // Argument node must also implement Element. (Note: we check + // against HTMLElement rather than Element for interop with prototype.js) + // Because 'document' is the 'parentNode' of 'body' + // it is frequently sent to this function even + // though it is not Element. + var gcs; + if(d.isWebKit){ + gcs = function(/*DomNode*/node){ + var s; + if(node instanceof HTMLElement){ + var dv = node.ownerDocument.defaultView; + s = dv.getComputedStyle(node, null); + if(!s && node.style){ + node.style.display = ""; + s = dv.getComputedStyle(node, null); + } + } + return s || {}; + }; + }else if(d.isIE){ + gcs = function(node){ + // IE (as of 7) doesn't expose Element like sane browsers + return node.nodeType == 1 /* ELEMENT_NODE*/ ? node.currentStyle : {}; + }; + }else{ + gcs = function(node){ + return node instanceof HTMLElement ? + node.ownerDocument.defaultView.getComputedStyle(node, null) : {}; + }; + } + dojo.getComputedStyle = gcs; + + if(!d.isIE){ + d._toPixelValue = function(element, value){ + // style values can be floats, client code may want + // to round for integer pixels. + return parseFloat(value) || 0; + }; + }else{ + d._toPixelValue = function(element, avalue){ + if(!avalue){ return 0; } + // on IE7, medium is usually 4 pixels + if(avalue == "medium"){ return 4; } + // style values can be floats, client code may + // want to round this value for integer pixels. + if(avalue.slice && avalue.slice(-2) == 'px'){ return parseFloat(avalue); } + with(element){ + var sLeft = style.left; + var rsLeft = runtimeStyle.left; + runtimeStyle.left = currentStyle.left; + try{ + // 'avalue' may be incompatible with style.left, which can cause IE to throw + // this has been observed for border widths using "thin", "medium", "thick" constants + // those particular constants could be trapped by a lookup + // but perhaps there are more + style.left = avalue; + avalue = style.pixelLeft; + }catch(e){ + avalue = 0; + } + style.left = sLeft; + runtimeStyle.left = rsLeft; + } + return avalue; + } + } + var px = d._toPixelValue; + + // FIXME: there opacity quirks on FF that we haven't ported over. Hrm. + /*===== + dojo._getOpacity = function(node){ + // summary: + // Returns the current opacity of the passed node as a + // floating-point value between 0 and 1. + // node: DomNode + // a reference to a DOM node. Does NOT support taking an + // ID string for speed reasons. + // returns: Number between 0 and 1 + return; // Number + } + =====*/ + + var astr = "DXImageTransform.Microsoft.Alpha"; + var af = function(n, f){ + try{ + return n.filters.item(astr); + }catch(e){ + return f ? {} : null; + } + } + + dojo._getOpacity = + d.isIE ? function(node){ + try{ + return af(node).Opacity / 100; // Number + }catch(e){ + return 1; // Number + } + } : + function(node){ + return gcs(node).opacity; + }; + + /*===== + dojo._setOpacity = function(node, opacity){ + // summary: + // set the opacity of the passed node portably. Returns the + // new opacity of the node. + // node: DOMNode + // a reference to a DOM node. Does NOT support taking an + // ID string for performance reasons. + // opacity: Number + // A Number between 0 and 1. 0 specifies transparent. + // returns: Number between 0 and 1 + return; // Number + } + =====*/ + + dojo._setOpacity = + d.isIE ? function(/*DomNode*/node, /*Number*/opacity){ + var ov = opacity * 100; + node.style.zoom = 1.0; + + // on IE7 Alpha(Filter opacity=100) makes text look fuzzy so disable it altogether (bug #2661), + //but still update the opacity value so we can get a correct reading if it is read later. + af(node, 1).Enabled = !(opacity == 1); + + if(!af(node)){ + node.style.filter += " progid:" + astr + "(Opacity=" + ov + ")"; + }else{ + af(node, 1).Opacity = ov; + } + + if(node.nodeName.toLowerCase() == "tr"){ + d.query("> td", node).forEach(function(i){ + d._setOpacity(i, opacity); + }); + } + return opacity; + } : + function(node, opacity){ + return node.style.opacity = opacity; + }; + + var _pixelNamesCache = { + left: true, top: true + }; + var _pixelRegExp = /margin|padding|width|height|max|min|offset/; // |border + var _toStyleValue = function(node, type, value){ + type = type.toLowerCase(); // FIXME: should we really be doing string case conversion here? Should we cache it? Need to profile! + if(d.isIE){ + if(value == "auto"){ + if(type == "height"){ return node.offsetHeight; } + if(type == "width"){ return node.offsetWidth; } + } + if(type == "fontweight"){ + switch(value){ + case 700: return "bold"; + case 400: + default: return "normal"; + } + } + } + if(!(type in _pixelNamesCache)){ + _pixelNamesCache[type] = _pixelRegExp.test(type); + } + return _pixelNamesCache[type] ? px(node, value) : value; + } + + var _floatStyle = d.isIE ? "styleFloat" : "cssFloat", + _floatAliases = { "cssFloat": _floatStyle, "styleFloat": _floatStyle, "float": _floatStyle } + ; + + // public API + + dojo.style = function( /*DomNode|String*/ node, + /*String?|Object?*/ style, + /*String?*/ value){ + // summary: + // Accesses styles on a node. If 2 arguments are + // passed, acts as a getter. If 3 arguments are passed, acts + // as a setter. + // description: + // Getting the style value uses the computed style for the node, so the value + // will be a calculated value, not just the immediate node.style value. + // Also when getting values, use specific style names, + // like "borderBottomWidth" instead of "border" since compound values like + // "border" are not necessarily reflected as expected. + // If you want to get node dimensions, use dojo.marginBox() or + // dojo.contentBox(). + // node: + // id or reference to node to get/set style for + // style: + // the style property to set in DOM-accessor format + // ("borderWidth", not "border-width") or an object with key/value + // pairs suitable for setting each property. + // value: + // If passed, sets value on the node for style, handling + // cross-browser concerns. When setting a pixel value, + // be sure to include "px" in the value. For instance, top: "200px". + // Otherwise, in some cases, some browsers will not apply the style. + // example: + // Passing only an ID or node returns the computed style object of + // the node: + // | dojo.style("thinger"); + // example: + // Passing a node and a style property returns the current + // normalized, computed value for that property: + // | dojo.style("thinger", "opacity"); // 1 by default + // + // example: + // Passing a node, a style property, and a value changes the + // current display of the node and returns the new computed value + // | dojo.style("thinger", "opacity", 0.5); // == 0.5 + // + // example: + // Passing a node, an object-style style property sets each of the values in turn and returns the computed style object of the node: + // | dojo.style("thinger", { + // | "opacity": 0.5, + // | "border": "3px solid black", + // | "height": "300px" + // | }); + // + // example: + // When the CSS style property is hyphenated, the JavaScript property is camelCased. + // font-size becomes fontSize, and so on. + // | dojo.style("thinger",{ + // | fontSize:"14pt", + // | letterSpacing:"1.2em" + // | }); + // + // example: + // dojo.NodeList implements .style() using the same syntax, omitting the "node" parameter, calling + // dojo.style() on every element of the list. See: dojo.query and dojo.NodeList + // | dojo.query(".someClassName").style("visibility","hidden"); + // | // or + // | dojo.query("#baz > div").style({ + // | opacity:0.75, + // | fontSize:"13pt" + // | }); + + var n = d.byId(node), args = arguments.length, op = (style == "opacity"); + style = _floatAliases[style] || style; + if(args == 3){ + return op ? d._setOpacity(n, value) : n.style[style] = value; /*Number*/ + } + if(args == 2 && op){ + return d._getOpacity(n); + } + var s = gcs(n); + if(args == 2 && !d.isString(style)){ + for(var x in style){ + d.style(node, x, style[x]); + } + return s; + } + return (args == 1) ? s : _toStyleValue(n, style, s[style] || n.style[style]); /* CSS2Properties||String||Number */ + } + + // ============================= + // Box Functions + // ============================= + + dojo._getPadExtents = function(/*DomNode*/n, /*Object*/computedStyle){ + // summary: + // Returns object with special values specifically useful for node + // fitting. + // + // * l/t = left/top padding (respectively) + // * w = the total of the left and right padding + // * h = the total of the top and bottom padding + // + // If 'node' has position, l/t forms the origin for child nodes. + // The w/h are used for calculating boxes. + // Normally application code will not need to invoke this + // directly, and will use the ...box... functions instead. + var + s = computedStyle||gcs(n), + l = px(n, s.paddingLeft), + t = px(n, s.paddingTop); + return { + l: l, + t: t, + w: l+px(n, s.paddingRight), + h: t+px(n, s.paddingBottom) + }; + } + + dojo._getBorderExtents = function(/*DomNode*/n, /*Object*/computedStyle){ + // summary: + // returns an object with properties useful for noting the border + // dimensions. + // + // * l/t = the sum of left/top border (respectively) + // * w = the sum of the left and right border + // * h = the sum of the top and bottom border + // + // The w/h are used for calculating boxes. + // Normally application code will not need to invoke this + // directly, and will use the ...box... functions instead. + var + ne = "none", + s = computedStyle||gcs(n), + bl = (s.borderLeftStyle != ne ? px(n, s.borderLeftWidth) : 0), + bt = (s.borderTopStyle != ne ? px(n, s.borderTopWidth) : 0); + return { + l: bl, + t: bt, + w: bl + (s.borderRightStyle!=ne ? px(n, s.borderRightWidth) : 0), + h: bt + (s.borderBottomStyle!=ne ? px(n, s.borderBottomWidth) : 0) + }; + } + + dojo._getPadBorderExtents = function(/*DomNode*/n, /*Object*/computedStyle){ + // summary: + // Returns object with properties useful for box fitting with + // regards to padding. + // + // * l/t = the sum of left/top padding and left/top border (respectively) + // * w = the sum of the left and right padding and border + // * h = the sum of the top and bottom padding and border + // + // The w/h are used for calculating boxes. + // Normally application code will not need to invoke this + // directly, and will use the ...box... functions instead. + var + s = computedStyle||gcs(n), + p = d._getPadExtents(n, s), + b = d._getBorderExtents(n, s); + return { + l: p.l + b.l, + t: p.t + b.t, + w: p.w + b.w, + h: p.h + b.h + }; + } + + dojo._getMarginExtents = function(n, computedStyle){ + // summary: + // returns object with properties useful for box fitting with + // regards to box margins (i.e., the outer-box). + // + // * l/t = marginLeft, marginTop, respectively + // * w = total width, margin inclusive + // * h = total height, margin inclusive + // + // The w/h are used for calculating boxes. + // Normally application code will not need to invoke this + // directly, and will use the ...box... functions instead. + var + s = computedStyle||gcs(n), + l = px(n, s.marginLeft), + t = px(n, s.marginTop), + r = px(n, s.marginRight), + b = px(n, s.marginBottom); + if(d.isWebKit && (s.position != "absolute")){ + // FIXME: Safari's version of the computed right margin + // is the space between our right edge and the right edge + // of our offsetParent. + // What we are looking for is the actual margin value as + // determined by CSS. + // Hack solution is to assume left/right margins are the same. + r = l; + } + return { + l: l, + t: t, + w: l+r, + h: t+b + }; + } + + // Box getters work in any box context because offsetWidth/clientWidth + // are invariant wrt box context + // + // They do *not* work for display: inline objects that have padding styles + // because the user agent ignores padding (it's bogus styling in any case) + // + // Be careful with IMGs because they are inline or block depending on + // browser and browser mode. + + // Although it would be easier to read, there are not separate versions of + // _getMarginBox for each browser because: + // 1. the branching is not expensive + // 2. factoring the shared code wastes cycles (function call overhead) + // 3. duplicating the shared code wastes bytes + + dojo._getMarginBox = function(/*DomNode*/node, /*Object*/computedStyle){ + // summary: + // returns an object that encodes the width, height, left and top + // positions of the node's margin box. + var s = computedStyle || gcs(node), me = d._getMarginExtents(node, s); + var l = node.offsetLeft - me.l, t = node.offsetTop - me.t, p = node.parentNode; + if(d.isMoz){ + // Mozilla: + // If offsetParent has a computed overflow != visible, the offsetLeft is decreased + // by the parent's border. + // We don't want to compute the parent's style, so instead we examine node's + // computed left/top which is more stable. + var sl = parseFloat(s.left), st = parseFloat(s.top); + if(!isNaN(sl) && !isNaN(st)){ + l = sl, t = st; + }else{ + // If child's computed left/top are not parseable as a number (e.g. "auto"), we + // have no choice but to examine the parent's computed style. + if(p && p.style){ + var pcs = gcs(p); + if(pcs.overflow != "visible"){ + var be = d._getBorderExtents(p, pcs); + l += be.l, t += be.t; + } + } + } + }else if(d.isOpera || (d.isIE > 7 && !d.isQuirks)){ + // On Opera and IE 8, offsetLeft/Top includes the parent's border + if(p){ + be = d._getBorderExtents(p); + l -= be.l; + t -= be.t; + } + } + return { + l: l, + t: t, + w: node.offsetWidth + me.w, + h: node.offsetHeight + me.h + }; + } + + dojo._getContentBox = function(node, computedStyle){ + // summary: + // Returns an object that encodes the width, height, left and top + // positions of the node's content box, irrespective of the + // current box model. + + // clientWidth/Height are important since the automatically account for scrollbars + // fallback to offsetWidth/Height for special cases (see #3378) + var s = computedStyle || gcs(node), + pe = d._getPadExtents(node, s), + be = d._getBorderExtents(node, s), + w = node.clientWidth, + h + ; + if(!w){ + w = node.offsetWidth, h = node.offsetHeight; + }else{ + h = node.clientHeight, be.w = be.h = 0; + } + // On Opera, offsetLeft includes the parent's border + if(d.isOpera){ pe.l += be.l; pe.t += be.t; }; + return { + l: pe.l, + t: pe.t, + w: w - pe.w - be.w, + h: h - pe.h - be.h + }; + } + + dojo._getBorderBox = function(node, computedStyle){ + var s = computedStyle || gcs(node), + pe = d._getPadExtents(node, s), + cb = d._getContentBox(node, s) + ; + return { + l: cb.l - pe.l, + t: cb.t - pe.t, + w: cb.w + pe.w, + h: cb.h + pe.h + }; + } + + // Box setters depend on box context because interpretation of width/height styles + // vary wrt box context. + // + // The value of dojo.boxModel is used to determine box context. + // dojo.boxModel can be set directly to change behavior. + // + // Beware of display: inline objects that have padding styles + // because the user agent ignores padding (it's a bogus setup anyway) + // + // Be careful with IMGs because they are inline or block depending on + // browser and browser mode. + // + // Elements other than DIV may have special quirks, like built-in + // margins or padding, or values not detectable via computedStyle. + // In particular, margins on TABLE do not seems to appear + // at all in computedStyle on Mozilla. + + dojo._setBox = function(/*DomNode*/node, /*Number?*/l, /*Number?*/t, /*Number?*/w, /*Number?*/h, /*String?*/u){ + // summary: + // sets width/height/left/top in the current (native) box-model + // dimentions. Uses the unit passed in u. + // node: DOM Node reference. Id string not supported for performance reasons. + // l: optional. left offset from parent. + // t: optional. top offset from parent. + // w: optional. width in current box model. + // h: optional. width in current box model. + // u: optional. unit measure to use for other measures. Defaults to "px". + u = u || "px"; + var s = node.style; + if(!isNaN(l)){ s.left = l + u; } + if(!isNaN(t)){ s.top = t + u; } + if(w >= 0){ s.width = w + u; } + if(h >= 0){ s.height = h + u; } + } + + dojo._isButtonTag = function(/*DomNode*/node) { + // summary: + // True if the node is BUTTON or INPUT.type="button". + return node.tagName == "BUTTON" + || node.tagName=="INPUT" && node.getAttribute("type").toUpperCase() == "BUTTON"; // boolean + } + + dojo._usesBorderBox = function(/*DomNode*/node){ + // summary: + // True if the node uses border-box layout. + + // We could test the computed style of node to see if a particular box + // has been specified, but there are details and we choose not to bother. + + // TABLE and BUTTON (and INPUT type=button) are always border-box by default. + // If you have assigned a different box to either one via CSS then + // box functions will break. + + var n = node.tagName; + return d.boxModel=="border-box" || n=="TABLE" || d._isButtonTag(node); // boolean + } + + dojo._setContentSize = function(/*DomNode*/node, /*Number*/widthPx, /*Number*/heightPx, /*Object*/computedStyle){ + // summary: + // Sets the size of the node's contents, irrespective of margins, + // padding, or borders. + if(d._usesBorderBox(node)){ + var pb = d._getPadBorderExtents(node, computedStyle); + if(widthPx >= 0){ widthPx += pb.w; } + if(heightPx >= 0){ heightPx += pb.h; } + } + d._setBox(node, NaN, NaN, widthPx, heightPx); + } + + dojo._setMarginBox = function(/*DomNode*/node, /*Number?*/leftPx, /*Number?*/topPx, + /*Number?*/widthPx, /*Number?*/heightPx, + /*Object*/computedStyle){ + // summary: + // sets the size of the node's margin box and placement + // (left/top), irrespective of box model. Think of it as a + // passthrough to dojo._setBox that handles box-model vagaries for + // you. + + var s = computedStyle || gcs(node), + // Some elements have special padding, margin, and box-model settings. + // To use box functions you may need to set padding, margin explicitly. + // Controlling box-model is harder, in a pinch you might set dojo.boxModel. + bb = d._usesBorderBox(node), + pb = bb ? _nilExtents : d._getPadBorderExtents(node, s) + ; + if(d.isWebKit){ + // on Safari (3.1.2), button nodes with no explicit size have a default margin + // setting an explicit size eliminates the margin. + // We have to swizzle the width to get correct margin reading. + if(d._isButtonTag(node)){ + var ns = node.style; + if(widthPx >= 0 && !ns.width) { ns.width = "4px"; } + if(heightPx >= 0 && !ns.height) { ns.height = "4px"; } + } + } + var mb = d._getMarginExtents(node, s); + if(widthPx >= 0){ widthPx = Math.max(widthPx - pb.w - mb.w, 0); } + if(heightPx >= 0){ heightPx = Math.max(heightPx - pb.h - mb.h, 0); } + d._setBox(node, leftPx, topPx, widthPx, heightPx); + } + + var _nilExtents = { l:0, t:0, w:0, h:0 }; + + // public API + + dojo.marginBox = function(/*DomNode|String*/node, /*Object?*/box){ + // summary: + // Getter/setter for the margin-box of node. + // description: + // Returns an object in the expected format of box (regardless + // if box is passed). The object might look like: + // `{ l: 50, t: 200, w: 300: h: 150 }` + // for a node offset from its parent 50px to the left, 200px from + // the top with a margin width of 300px and a margin-height of + // 150px. + // node: + // id or reference to DOM Node to get/set box for + // box: + // If passed, denotes that dojo.marginBox() should + // update/set the margin box for node. Box is an object in the + // above format. All properties are optional if passed. + var n = d.byId(node), s = gcs(n), b = box; + return !b ? d._getMarginBox(n, s) : d._setMarginBox(n, b.l, b.t, b.w, b.h, s); // Object + } + + dojo.contentBox = function(/*DomNode|String*/node, /*Object?*/box){ + // summary: + // Getter/setter for the content-box of node. + // description: + // Returns an object in the expected format of box (regardless if box is passed). + // The object might look like: + // `{ l: 50, t: 200, w: 300: h: 150 }` + // for a node offset from its parent 50px to the left, 200px from + // the top with a content width of 300px and a content-height of + // 150px. Note that the content box may have a much larger border + // or margin box, depending on the box model currently in use and + // CSS values set/inherited for node. + // node: + // id or reference to DOM Node to get/set box for + // box: + // If passed, denotes that dojo.contentBox() should + // update/set the content box for node. Box is an object in the + // above format. All properties are optional if passed. + var n = d.byId(node), s = gcs(n), b = box; + return !b ? d._getContentBox(n, s) : d._setContentSize(n, b.w, b.h, s); // Object + } + + // ============================= + // Positioning + // ============================= + + var _sumAncestorProperties = function(node, prop){ + if(!(node = (node||0).parentNode)){return 0} + var val, retVal = 0, _b = d.body(); + while(node && node.style){ + if(gcs(node).position == "fixed"){ + return 0; + } + val = node[prop]; + if(val){ + retVal += val - 0; + // opera and khtml #body & #html has the same values, we only + // need one value + if(node == _b){ break; } + } + node = node.parentNode; + } + return retVal; // integer + } + + dojo._docScroll = function(){ + var + _b = d.body(), + _w = d.global, + de = d.doc.documentElement; + return { + y: (_w.pageYOffset || de.scrollTop || _b.scrollTop || 0), + x: (_w.pageXOffset || d._fixIeBiDiScrollLeft(de.scrollLeft) || _b.scrollLeft || 0) + }; + }; + + dojo._isBodyLtr = function(){ + //FIXME: could check html and body tags directly instead of computed style? need to ignore case, accept empty values + return ("_bodyLtr" in d) ? d._bodyLtr : + d._bodyLtr = gcs(d.body()).direction == "ltr"; // Boolean + } + + dojo._getIeDocumentElementOffset = function(){ + // summary + // The following values in IE contain an offset: + // event.clientX + // event.clientY + // node.getBoundingClientRect().left + // node.getBoundingClientRect().top + // But other position related values do not contain this offset, such as + // node.offsetLeft, node.offsetTop, node.style.left and node.style.top. + // The offset is always (2, 2) in LTR direction. When the body is in RTL + // direction, the offset counts the width of left scroll bar's width. + // This function computes the actual offset. + + //NOTE: assumes we're being called in an IE browser + + var de = d.doc.documentElement; + //FIXME: use this instead? var de = d.compatMode == "BackCompat" ? d.body : d.documentElement; + + if(d.isIE < 7){ + return { x: d._isBodyLtr() || window.parent == window ? + de.clientLeft : de.offsetWidth - de.clientWidth - de.clientLeft, + y: de.clientTop }; // Object + }else if(d.isIE < 8){ + return {x: de.getBoundingClientRect().left, y: de.getBoundingClientRect().top}; + }else{ + return { + x: 0, + y: 0 + }; + } + + }; + + dojo._fixIeBiDiScrollLeft = function(/*Integer*/ scrollLeft){ + // In RTL direction, scrollLeft should be a negative value, but IE < 8 + // returns a positive one. All codes using documentElement.scrollLeft + // must call this function to fix this error, otherwise the position + // will offset to right when there is a horizontal scrollbar. + + var dd = d.doc; + if(d.isIE < 8 && !d._isBodyLtr()){ + var de = dd.compatMode == "BackCompat" ? dd.body : dd.documentElement; + return scrollLeft + de.clientWidth - de.scrollWidth; // Integer + } + return scrollLeft; // Integer + } + + dojo._abs = function(/*DomNode*/node, /*Boolean?*/includeScroll){ + // summary: + // Gets the position of the passed element relative to + // the viewport (if includeScroll==false), or relative to the + // document root (if includeScroll==true). + // + // Returns an object of the form: + // { x: 100, y: 300 } + // if includeScroll is passed, the x and y values will include any + // document offsets that may affect the position relative to the + // viewport. + + // FIXME: need to decide in the brave-new-world if we're going to be + // margin-box or border-box. + + // targetBoxType == "border-box" + var db = d.body(), dh = d.body().parentNode, ret; + if(node["getBoundingClientRect"]){ + // IE6+, FF3+, super-modern WebKit, and Opera 9.6+ all take this branch + var client = node.getBoundingClientRect(); + ret = { x: client.left, y: client.top }; + if(d.isFF >= 3){ + // in FF3 you have to subtract the document element margins + var cs = gcs(dh); + ret.x -= px(dh, cs.marginLeft) + px(dh, cs.borderLeftWidth); + ret.y -= px(dh, cs.marginTop) + px(dh, cs.borderTopWidth); + } + if(d.isIE){ + // On IE there's a 2px offset that we need to adjust for, see _getIeDocumentElementOffset() + var offset = d._getIeDocumentElementOffset(); + + // fixes the position in IE, quirks mode + ret.x -= offset.x + (d.isQuirks ? db.clientLeft : 0); + ret.y -= offset.y + (d.isQuirks ? db.clientTop : 0); + } + }else{ + // FF2 and Safari + ret = { + x: 0, + y: 0 + }; + if(node["offsetParent"]){ + ret.x -= _sumAncestorProperties(node, "scrollLeft"); + ret.y -= _sumAncestorProperties(node, "scrollTop"); + + var curnode = node; + do{ + var n = curnode.offsetLeft, + t = curnode.offsetTop; + ret.x += isNaN(n) ? 0 : n; + ret.y += isNaN(t) ? 0 : t; + + cs = gcs(curnode); + if(curnode != node){ + if(d.isFF){ + // tried left+right with differently sized left/right borders + // it really is 2xleft border in FF, not left+right, even in RTL! + ret.x += 2 * px(curnode,cs.borderLeftWidth); + ret.y += 2 * px(curnode,cs.borderTopWidth); + }else{ + ret.x += px(curnode, cs.borderLeftWidth); + ret.y += px(curnode, cs.borderTopWidth); + } + } + // static children in a static div in FF2 are affected by the div's border as well + // but offsetParent will skip this div! + if(d.isFF && cs.position=="static"){ + var parent=curnode.parentNode; + while(parent!=curnode.offsetParent){ + var pcs=gcs(parent); + if(pcs.position=="static"){ + ret.x += px(curnode,pcs.borderLeftWidth); + ret.y += px(curnode,pcs.borderTopWidth); + } + parent=parent.parentNode; + } + } + curnode = curnode.offsetParent; + }while((curnode != dh) && curnode); + }else if(node.x && node.y){ + ret.x += isNaN(node.x) ? 0 : node.x; + ret.y += isNaN(node.y) ? 0 : node.y; + } + } + // account for document scrolling + // if offsetParent is used, ret value already includes scroll position + // so we may have to actually remove that value if !includeScroll + if(includeScroll){ + var scroll = d._docScroll(); + ret.x += scroll.x; + ret.y += scroll.y; + } + + return ret; // Object + } + + // FIXME: need a setter for coords or a moveTo!! + dojo.coords = function(/*DomNode|String*/node, /*Boolean?*/includeScroll){ + // summary: + // Returns an object that measures margin box width/height and + // absolute positioning data from dojo._abs(). + // + // description: + // Returns an object that measures margin box width/height and + // absolute positioning data from dojo._abs(). + // Return value will be in the form: + // `{ l: 50, t: 200, w: 300: h: 150, x: 100, y: 300 }` + // Does not act as a setter. If includeScroll is passed, the x and + // y params are affected as one would expect in dojo._abs(). + var n = d.byId(node), s = gcs(n), mb = d._getMarginBox(n, s); + var abs = d._abs(n, includeScroll); + mb.x = abs.x; + mb.y = abs.y; + return mb; + } + + // ============================= + // Element attribute Functions + // ============================= + + var ieLT8 = d.isIE < 8; + + var _fixAttrName = function(/*String*/name){ + switch(name.toLowerCase()){ + // Internet Explorer will only set or remove tabindex/readonly + // if it is spelled "tabIndex"/"readOnly" + case "tabindex": + return ieLT8 ? "tabIndex" : "tabindex"; + case "readonly": + return "readOnly"; + case "class": + return "className"; + case "for": case "htmlfor": + // to pick up for attrib set in markup via getAttribute() IE<8 uses "htmlFor" and others use "for" + // get/setAttribute works in all as long use same value for both get/set + return ieLT8 ? "htmlFor" : "for"; + default: + return name; + } + } + + // non-deprecated HTML4 attributes with default values + // http://www.w3.org/TR/html401/index/attributes.html + // FF and Safari will return the default values if you + // access the attributes via a property but not + // via getAttribute() + var _attrProps = { + colspan: "colSpan", + enctype: "enctype", + frameborder: "frameborder", + method: "method", + rowspan: "rowSpan", + scrolling: "scrolling", + shape: "shape", + span: "span", + type: "type", + valuetype: "valueType", + // the following attributes don't have the default but should be treated like properties + classname: "className", + innerhtml: "innerHTML" + } + + dojo.hasAttr = function(/*DomNode|String*/node, /*String*/name){ + // summary: + // Returns true if the requested attribute is specified on the + // given element, and false otherwise. + // node: + // id or reference to the element to check + // name: + // the name of the attribute + // returns: + // true if the requested attribute is specified on the + // given element, and false otherwise + node = d.byId(node); + var fixName = _fixAttrName(name); + fixName = fixName == "htmlFor" ? "for" : fixName; //IE<8 uses htmlFor except in this case + var attr = node.getAttributeNode && node.getAttributeNode(fixName); + return attr ? attr.specified : false; // Boolean + } + + var _evtHdlrMap = {}, _ctr = 0, + _attrId = dojo._scopeName + "attrid", + // the next dictionary lists elements with read-only innerHTML on IE + _roInnerHtml = {col: 1, colgroup: 1, + // frameset: 1, head: 1, html: 1, style: 1, + table: 1, tbody: 1, tfoot: 1, thead: 1, tr: 1, title: 1}; + + dojo.attr = function(/*DomNode|String*/node, /*String|Object*/name, /*String?*/value){ + // summary: + // Gets or sets an attribute on an HTML element. + // description: + // Handles normalized getting and setting of attributes on DOM + // Nodes. If 2 arguments are passed, and a the second argumnt is a + // string, acts as a getter. + // + // If a third argument is passed, or if the second argumnt is a + // map of attributes, acts as a setter. + // + // When passing functions as values, note that they will not be + // directly assigned to slots on the node, but rather the default + // behavior will be removed and the new behavior will be added + // using `dojo.connect()`, meaning that event handler properties + // will be normalized and that some caveats with regards to + // non-standard behaviors for onsubmit apply. Namely that you + // should cancel form submission using `dojo.stopEvent()` on the + // passed event object instead of returning a boolean value from + // the handler itself. + // node: + // id or reference to the element to get or set the attribute on + // name: + // the name of the attribute to get or set. + // value: + // The value to set for the attribute + // returns: + // when used as a getter, the value of the requested attribute + // or null if that attribute does not have a specified or + // default value; + // + // when used as a setter, undefined + // + // example: + // | // get the current value of the "foo" attribute on a node + // | dojo.attr(dojo.byId("nodeId"), "foo"); + // | // or we can just pass the id: + // | dojo.attr("nodeId", "foo"); + // + // example: + // | // use attr() to set the tab index + // | dojo.attr("nodeId", "tabindex", 3); + // | + // + // example: + // Set multiple values at once, including event handlers: + // | dojo.attr("formId", { + // | "foo": "bar", + // | "tabindex": -1, + // | "method": "POST", + // | "onsubmit": function(e){ + // | // stop submitting the form. Note that the IE behavior + // | // of returning true or false will have no effect here + // | // since our handler is connect()ed to the built-in + // | // onsubmit behavior and so we need to use + // | // dojo.stopEvent() to ensure that the submission + // | // doesn't proceed. + // | dojo.stopEvent(e); + // | + // | // submit the form with Ajax + // | dojo.xhrPost({ form: "formId" }); + // | } + // | }); + // + // example: + // Style is s special case: Only set with an object hash of styles + // | dojo.attr("someNode",{ + // | id:"bar", + // | style:{ + // | width:"200px", height:"100px", color:"#000" + // | } + // | }); + // + // example: + // Again, only set style as an object hash of styles: + // | var obj = { color:"#fff", backgroundColor:"#000" }; + // | dojo.attr("someNode", "style", obj); + // | + // | // though shorter to use `dojo.style` in this case: + // | dojo.style("someNode", obj); + + node = d.byId(node); + var args = arguments.length; + if(args == 2 && !d.isString(name)){ + // the object form of setter: the 2nd argument is a dictionary + for(var x in name){ d.attr(node, x, name[x]); } + // FIXME: return the node in this case? could be useful. + return; + } + name = _fixAttrName(name); + if(args == 3){ // setter + if(d.isFunction(value)){ + // clobber if we can + var attrId = d.attr(node, _attrId); + if(!attrId){ + attrId = _ctr++; + d.attr(node, _attrId, attrId); + } + if(!_evtHdlrMap[attrId]){ + _evtHdlrMap[attrId] = {}; + } + var h = _evtHdlrMap[attrId][name]; + if(h){ + d.disconnect(h); + }else{ + try{ + delete node[name]; + }catch(e){} + } + + // ensure that event objects are normalized, etc. + _evtHdlrMap[attrId][name] = d.connect(node, name, value); + + }else if(typeof value == "boolean"){ // e.g. onsubmit, disabled + node[name] = value; + }else if(name === "style" && !d.isString(value)){ + // when the name is "style" and value is an object, pass along + d.style(node, value); + }else if(name == "className"){ + node.className = value; + }else if(name === "innerHTML"){ + if(d.isIE && node.tagName.toLowerCase() in _roInnerHtml){ + d.empty(node); + node.appendChild(d._toDom(value, node.ownerDocument)); + }else{ + node[name] = value; + } + }else{ + node.setAttribute(name, value); + } + }else{ + // getter + // should we access this attribute via a property or + // via getAttribute()? + var prop = _attrProps[name.toLowerCase()]; + if(prop){ + return node[prop]; + } + var attrValue = node[name]; + return (typeof attrValue == 'boolean' || typeof attrValue == 'function') ? attrValue + : (d.hasAttr(node, name) ? node.getAttribute(name) : null); + } + } + + dojo.removeAttr = function(/*DomNode|String*/node, /*String*/name){ + // summary: + // Removes an attribute from an HTML element. + // node: + // id or reference to the element to remove the attribute from + // name: + // the name of the attribute to remove + d.byId(node).removeAttribute(_fixAttrName(name)); + } + + dojo.create = function(tag, attrs, refNode, pos){ + // summary: Create an element, allowing for optional attribute decoration + // and placement. + // + // description: + // A DOM Element creation function. A shorthand method for creating a node or + // a fragment, and allowing for a convenient optional attribute setting step, + // as well as an optional DOM placement reference. + //| + // Attributes are set by passing the optional object through `dojo.attr`. + // See `dojo.attr` for noted caveats and nuances, and API if applicable. + //| + // Placement is done via `dojo.place`, assuming the new node to be the action + // node, passing along the optional reference node and position. + // + // tag: String|DomNode + // A string of the element to create (eg: "div", "a", "p", "li", "script", "br"), + // or an existing DOM node to process. + // + // attrs: Object + // An object-hash of attributes to set on the newly created node. + // Can be null, if you don't want to set any attributes/styles. + // See: `dojo.attr` for a description of available attributes. + // + // refNode: String?|DomNode? + // Optional reference node. Used by `dojo.place` to place the newly created + // node somewhere in the dom relative to refNode. Can be a DomNode reference + // or String ID of a node. + // + // pos: String? + // Optional positional reference. Defaults to "last" by way of `dojo.place`, + // though can be set to "first","after","before","last", "replace" or "only" + // to further control the placement of the new node relative to the refNode. + // 'refNode' is required if a 'pos' is specified. + // + // returns: DomNode + // + // example: + // Create a DIV: + // | var n = dojo.create("div"); + // + // example: + // Create a DIV with content: + // | var n = dojo.create("div", { innerHTML:"<p>hi</p>" }); + // + // example: + // Place a new DIV in the BODY, with no attributes set + // | var n = dojo.create("div", null, dojo.body()); + // + // example: + // Create an UL, and populate it with LI's. Place the list as the first-child of a + // node with id="someId": + // | var ul = dojo.create("ul", null, "someId", "first"); + // | var items = ["one", "two", "three", "four"]; + // | dojo.forEach(items, function(data){ + // | dojo.create("li", { innerHTML: data }, ul); + // | }); + // + // example: + // Create an anchor, with an href. Place in BODY: + // | dojo.create("a", { href:"foo.html", title:"Goto FOO!" }, dojo.body()); + // + // example: + // Create a `dojo.NodeList` from a new element (for syntatic sugar): + // | dojo.query(dojo.create('div')) + // | .addClass("newDiv") + // | .onclick(function(e){ }) + // | .place("#someNode"); // redundant, but cleaner. + + var doc = d.doc; + if(refNode){ + refNode = d.byId(refNode); + doc = refNode.ownerDocument; + } + if(d.isString(tag)){ + tag = doc.createElement(tag); + } + if(attrs){ d.attr(tag, attrs); } + if(refNode){ d.place(tag, refNode, pos); } + return tag; // DomNode + } + + /*===== + dojo.empty = function(node){ + // summary: + // safely removes all children of the node. + // node: DOMNode|String + // a reference to a DOM node or an id. + // example: + // Destroy node's children byId: + // | dojo.empty("someId"); + // + // example: + // Destroy all nodes' children in a list by reference: + // | dojo.query(".someNode").forEach(dojo.empty); + } + =====*/ + + d.empty = + d.isIE ? function(node){ + node = d.byId(node); + for(var c; c = node.lastChild;){ // intentional assignment + d.destroy(c); + } + } : + function(node){ + d.byId(node).innerHTML = ""; + }; + + /*===== + dojo._toDom = function(frag, doc){ + // summary: + // instantiates an HTML fragment returning the corresponding DOM. + // frag: String + // the HTML fragment + // doc: DocumentNode? + // optional document to use when creating DOM nodes, defaults to + // dojo.doc if not specified. + // returns: DocumentFragment + // + // example: + // Create a table row: + // | var tr = dojo._toDom("<tr><td>First!</td></tr>"); + } + =====*/ + + // support stuff for dojo._toDom + var tagWrap = { + option: ["select"], + tbody: ["table"], + thead: ["table"], + tfoot: ["table"], + tr: ["table", "tbody"], + td: ["table", "tbody", "tr"], + th: ["table", "thead", "tr"], + legend: ["fieldset"], + caption: ["table"], + colgroup: ["table"], + col: ["table", "colgroup"], + li: ["ul"] + }, + reTag = /<\s*([\w\:]+)/, + masterNode = {}, masterNum = 0, + masterName = "__" + d._scopeName + "ToDomId"; + + // generate start/end tag strings to use + // for the injection for each special tag wrap case. + for(var param in tagWrap){ + var tw = tagWrap[param]; + tw.pre = param == "option" ? '<select multiple="multiple">' : "<" + tw.join("><") + ">"; + tw.post = "</" + tw.reverse().join("></") + ">"; + // the last line is destructive: it reverses the array, + // but we don't care at this point + } + + d._toDom = function(frag, doc){ + // summary converts HTML string into DOM nodes. + + doc = doc || d.doc; + var masterId = doc[masterName]; + if(!masterId){ + doc[masterName] = masterId = ++masterNum + ""; + masterNode[masterId] = doc.createElement("div"); + } + + // make sure the frag is a string. + frag += ""; + + // find the starting tag, and get node wrapper + var match = frag.match(reTag), + tag = match ? match[1].toLowerCase() : "", + master = masterNode[masterId], + wrap, i, fc, df; + if(match && tagWrap[tag]){ + wrap = tagWrap[tag]; + master.innerHTML = wrap.pre + frag + wrap.post; + for(i = wrap.length; i; --i){ + master = master.firstChild; + } + }else{ + master.innerHTML = frag; + } + + // one node shortcut => return the node itself + if(master.childNodes.length == 1){ + return master.removeChild(master.firstChild); // DOMNode + } + + // return multiple nodes as a document fragment + df = doc.createDocumentFragment(); + while(fc = master.firstChild){ // intentional assignment + df.appendChild(fc); + } + return df; // DOMNode + } + + // ============================= + // (CSS) Class Functions + // ============================= + var _className = "className"; + + dojo.hasClass = function(/*DomNode|String*/node, /*String*/classStr){ + // summary: + // Returns whether or not the specified classes are a portion of the + // class list currently applied to the node. + // + // node: + // String ID or DomNode reference to check the class for. + // + // classStr: + // A string class name to look for. + // + // example: + // | if(dojo.hasClass("someNode","aSillyClassName")){ ... } + + return ((" "+ d.byId(node)[_className] +" ").indexOf(" "+ classStr +" ") >= 0); // Boolean + }; + + dojo.addClass = function(/*DomNode|String*/node, /*String*/classStr){ + // summary: + // Adds the specified classes to the end of the class list on the + // passed node. Will not re-apply duplicate classes, except in edge + // cases when adding multiple classes at once. + // + // node: String ID or DomNode reference to add a class string too + // classStr: A String class name to add + // + // example: + // Add A class to some node: + // | dojo.addClass("someNode", "anewClass"); + // + // example: + // Add two classes at once (could potentially add duplicate): + // | dojo.addClass("someNode", "firstClass secondClass"); + // + // example: + // Available in `dojo.NodeList` for multiple additions + // | dojo.query("ul > li").addClass("firstLevel"); + + node = d.byId(node); + var cls = node[_className]; + if((" "+ cls +" ").indexOf(" " + classStr + " ") < 0){ + node[_className] = cls + (cls ? ' ' : '') + classStr; + } + }; + + dojo.removeClass = function(/*DomNode|String*/node, /*String*/classStr){ + // summary: Removes the specified classes from node. No `dojo.hasClass` + // check is required. + // + // node: String ID or DomNode reference to remove the class from. + // + // classString: String class name to remove + // + // example: + // | dojo.removeClass("someNode", "firstClass"); + // + // example: + // Available in `dojo.NodeList` for multiple removal + // | dojo.query(".foo").removeClass("foo"); + + node = d.byId(node); + var t = d.trim((" " + node[_className] + " ").replace(" " + classStr + " ", " ")); + if(node[_className] != t){ node[_className] = t; } + }; + + dojo.toggleClass = function(/*DomNode|String*/node, /*String*/classStr, /*Boolean?*/condition){ + // summary: + // Adds a class to node if not present, or removes if present. + // Pass a boolean condition if you want to explicitly add or remove. + // condition: + // If passed, true means to add the class, false means to remove. + // + // example: + // | dojo.toggleClass("someNode", "hovered"); + // + // example: + // Forcefully add a class + // | dojo.toggleClass("someNode", "hovered", true); + // + // example: + // Available in `dojo.NodeList` for multiple toggles + // | dojo.query(".toggleMe").toggleClass("toggleMe"); + + if(condition === undefined){ + condition = !d.hasClass(node, classStr); + } + d[condition ? "addClass" : "removeClass"](node, classStr); + }; + +})(); + +} + +if(!dojo._hasResource["dojo._base.NodeList"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.NodeList"] = true; +dojo.provide("dojo._base.NodeList"); + + + +(function(){ + + var d = dojo; + + var ap = Array.prototype, aps = ap.slice, apc = ap.concat; + + var tnl = function(a){ + // decorate an array to make it look like a NodeList + a.constructor = d.NodeList; + dojo._mixin(a, d.NodeList.prototype); + return a; + }; + + var loopBody = function(f, a, o){ + a = [0].concat(aps.call(a, 0)); + o = o || d.global; + return function(node){ + a[0] = node; + return f.apply(o, a); + }; + }; + + // adapters + + var adaptAsForEach = function(f, o){ + // summary: + // adapts a single node function to be used in the forEach-type + // actions. The initial object is returned from the specialized + // function. + // f: Function + // a function to adapt + // o: Object? + // an optional context for f + return function(){ + this.forEach(loopBody(f, arguments, o)); + return this; // Object + }; + }; + + var adaptAsMap = function(f, o){ + // summary: + // adapts a single node function to be used in the map-type + // actions. The return is a new array of values, as via `dojo.map` + // f: Function + // a function to adapt + // o: Object? + // an optional context for f + return function(){ + return this.map(loopBody(f, arguments, o)); + }; + }; + + var adaptAsFilter = function(f, o){ + // summary: + // adapts a single node function to be used in the filter-type actions + // f: Function + // a function to adapt + // o: Object? + // an optional context for f + return function(){ + return this.filter(loopBody(f, arguments, o)); + }; + }; + + var adaptWithCondition = function(f, g, o){ + // summary: + // adapts a single node function to be used in the map-type + // actions, behaves like forEach() or map() depending on arguments + // f: Function + // a function to adapt + // g: Function + // a condition function, if true runs as map(), otherwise runs as forEach() + // o: Object? + // an optional context for f and g + return function(){ + var a = arguments, body = loopBody(f, a, o); + if(g.call(o || d.global, a)){ + return this.map(body); // self + } + this.forEach(body); + return this; // self + }; + }; + + var magicGuard = function(a){ + // summary: + // the guard function for dojo.attr() and dojo.style() + return a.length == 1 && d.isString(a[0]) + }; + + var orphan = function(node){ + // summary: + // function to orphan nodes + var p = node.parentNode; + if(p){ + p.removeChild(node); + } + }; + // FIXME: should we move orphan() to dojo.html? + + dojo.NodeList = function(){ + // summary: + // dojo.NodeList is an of Array subclass which adds syntactic + // sugar for chaining, common iteration operations, animation, and + // node manipulation. NodeLists are most often returned as the + // result of dojo.query() calls. + // description: + // dojo.NodeList instances provide many utilities that reflect + // core Dojo APIs for Array iteration and manipulation, DOM + // manipulation, and event handling. Instead of needing to dig up + // functions in the dojo.* namespace, NodeLists generally make the + // full power of Dojo available for DOM manipulation tasks in a + // simple, chainable way. + // example: + // create a node list from a node + // | new dojo.NodeList(dojo.byId("foo")); + // example: + // get a NodeList from a CSS query and iterate on it + // | var l = dojo.query(".thinger"); + // | l.forEach(function(node, index, nodeList){ + // | + // | }); + // example: + // use native and Dojo-provided array methods to manipulate a + // NodeList without needing to use dojo.* functions explicitly: + // | var l = dojo.query(".thinger"); + // | // since NodeLists are real arrays, they have a length + // | // property that is both readable and writable and + // | // push/pop/shift/unshift methods + // | + // | l.push(dojo.create("<span>howdy!</span>")); + // | + // | // dojo's normalized array methods work too: + // | + // | // ...including the special "function as string" shorthand + // | + // | + // | // NodeLists can be [..] indexed, or you can use the at() + // | // function to get specific items wrapped in a new NodeList: + // | var node = l[3]; // the 4th element + // | var newList = l.at(1, 3); // the 2nd and 4th elements + // example: + // the style functions you expect are all there too: + // | // style() as a getter... + // | var borders = dojo.query(".thinger").style("border"); + // | // ...and as a setter: + // | dojo.query(".thinger").style("border", "1px solid black"); + // | // class manipulation + // | dojo.query("li:nth-child(even)").addClass("even"); + // | // even getting the coordinates of all the items + // | var coords = dojo.query(".thinger").coords(); + // example: + // DOM manipulation functions from the dojo.* namespace area also + // available: + // | // remove all of the elements in the list from their + // | // parents (akin to "deleting" them from the document) + // | dojo.query(".thinger").orphan(); + // | // place all elements in the list at the front of #foo + // | dojo.query(".thinger").place("foo", "first"); + // example: + // Event handling couldn't be easier. `dojo.connect` is mapped in, + // and shortcut handlers are provided for most DOM events: + // | // like dojo.connect(), but with implicit scope + // | dojo.query("li").connect("onclick", console, "log"); + // | + // | // many common event handlers are already available directly: + // | dojo.query("li").onclick(console, "log"); + // | var toggleHovered = dojo.hitch(dojo, "toggleClass", "hovered"); + // | dojo.query("p") + // | .onmouseenter(toggleHovered) + // | .onmouseleave(toggleHovered); + // example: + // chainability is a key advantage of NodeLists: + // | dojo.query(".thinger") + // | .onclick(function(e){ /* ... */ }) + // | .at(1, 3, 8) // get a subset + // | .style("padding", "5px") + // | .forEach(console.log); + + return tnl(Array.apply(null, arguments)); + }; + + var nl = d.NodeList, nlp = nl.prototype; + + // expose adapters and the wrapper as private functions + + nl._wrap = tnl; + nl._adaptAsMap = adaptAsMap; + nl._adaptAsForEach = adaptAsForEach; + nl._adaptAsFilter = adaptAsFilter; + nl._adaptWithCondition = adaptWithCondition; + + // mass assignment + + // add array redirectors + d.forEach(["slice", "splice"], function(name){ + var f = ap[name]; + nlp[name] = function(){ return tnl(f.apply(this, arguments)); }; + }); + // concat should be here but some browsers with native NodeList have problems with it + + // add array.js redirectors + d.forEach(["indexOf", "lastIndexOf", "every", "some"], function(name){ + var f = d[name]; + nlp[name] = function(){ return f.apply(d, [this].concat(aps.call(arguments, 0))); }; + }); + + // add conditional methods + d.forEach(["attr", "style"], function(name){ + nlp[name] = adaptWithCondition(d[name], magicGuard); + }); + + // add forEach actions + d.forEach(["connect", "addClass", "removeClass", "toggleClass", "empty"], function(name){ + nlp[name] = adaptAsForEach(d[name]); + }); + + dojo.extend(dojo.NodeList, { + // http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array#Methods + + // FIXME: handle return values for #3244 + // http://trac.dojotoolkit.org/ticket/3244 + + // FIXME: + // need to wrap or implement: + // join (perhaps w/ innerHTML/outerHTML overload for toString() of items?) + // reduce + // reduceRight + + /*===== + slice: function(begin, end){ + // summary: + // Returns a new NodeList, maintaining this one in place + // description: + // This method behaves exactly like the Array.slice method + // with the caveat that it returns a dojo.NodeList and not a + // raw Array. For more details, see Mozilla's (slice + // documentation)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:slice] + // begin: Integer + // Can be a positive or negative integer, with positive + // integers noting the offset to begin at, and negative + // integers denoting an offset from the end (i.e., to the left + // of the end) + // end: Integer? + // Optional parameter to describe what position relative to + // the NodeList's zero index to end the slice at. Like begin, + // can be positive or negative. + return tnl(a.slice.apply(this, arguments)); + }, + + splice: function(index, howmany, item){ + // summary: + // Returns a new NodeList, manipulating this NodeList based on + // the arguments passed, potentially splicing in new elements + // at an offset, optionally deleting elements + // description: + // This method behaves exactly like the Array.splice method + // with the caveat that it returns a dojo.NodeList and not a + // raw Array. For more details, see Mozilla's (splice + // documentation)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:splice] + // index: Integer + // begin can be a positive or negative integer, with positive + // integers noting the offset to begin at, and negative + // integers denoting an offset from the end (i.e., to the left + // of the end) + // howmany: Integer? + // Optional parameter to describe what position relative to + // the NodeList's zero index to end the slice at. Like begin, + // can be positive or negative. + // item: Object...? + // Any number of optional parameters may be passed in to be + // spliced into the NodeList + // returns: + // dojo.NodeList + return tnl(a.splice.apply(this, arguments)); + }, + + indexOf: function(value, fromIndex){ + // summary: + // see dojo.indexOf(). The primary difference is that the acted-on + // array is implicitly this NodeList + // value: Object: + // The value to search for. + // fromIndex: Integer?: + // The loction to start searching from. Optional. Defaults to 0. + // description: + // For more details on the behavior of indexOf, see Mozilla's + // (indexOf + // docs)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:indexOf] + // returns: + // Positive Integer or 0 for a match, -1 of not found. + return d.indexOf(this, value, fromIndex); // Integer + }, + + lastIndexOf: function(value, fromIndex){ + // summary: + // see dojo.lastIndexOf(). The primary difference is that the + // acted-on array is implicitly this NodeList + // description: + // For more details on the behavior of lastIndexOf, see + // Mozilla's (lastIndexOf + // docs)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:lastIndexOf] + // value: Object + // The value to search for. + // fromIndex: Integer? + // The loction to start searching from. Optional. Defaults to 0. + // returns: + // Positive Integer or 0 for a match, -1 of not found. + return d.lastIndexOf(this, value, fromIndex); // Integer + }, + + every: function(callback, thisObject){ + // summary: + // see `dojo.every()` and the (Array.every + // docs)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:every]. + // Takes the same structure of arguments and returns as + // dojo.every() with the caveat that the passed array is + // implicitly this NodeList + // callback: Function: the callback + // thisObject: Object?: the context + return d.every(this, callback, thisObject); // Boolean + }, + + some: function(callback, thisObject){ + // summary: + // Takes the same structure of arguments and returns as + // `dojo.some()` with the caveat that the passed array is + // implicitly this NodeList. See `dojo.some()` and Mozilla's + // (Array.some + // documentation)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:some]. + // callback: Function: the callback + // thisObject: Object?: the context + return d.some(this, callback, thisObject); // Boolean + }, + =====*/ + + concat: function(item){ + // summary: + // Returns a new NodeList comprised of items in this NodeList + // as well as items passed in as parameters + // description: + // This method behaves exactly like the Array.concat method + // with the caveat that it returns a `dojo.NodeList` and not a + // raw Array. For more details, see the (Array.concat + // docs)[http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array:concat] + // item: Object? + // Any number of optional parameters may be passed in to be + // spliced into the NodeList + // returns: + // dojo.NodeList + + //return tnl(apc.apply(this, arguments)); + // the line above won't work for the native NodeList :-( + + // implementation notes: + // 1) Native NodeList is not an array, and cannot be used directly + // in concat() --- the latter doesn't recognize it as an array, and + // does not inline it, but append as a single entity. + // 2) On some browsers (e.g., Safari) the "constructor" property is + // read-only and cannot be changed. So we have to test for both + // native NodeList and dojo.NodeList in this property to recognize + // the node list. + + var t = d.isArray(this) ? this : aps.call(this, 0), + m = d.map(arguments, function(a){ + return a && !d.isArray(a) && + (a.constructor === NodeList || a.constructor == nl) ? + aps.call(a, 0) : a; + }); + return tnl(apc.apply(t, m)); // dojo.NodeList + }, + + map: function(/*Function*/ func, /*Function?*/ obj){ + // summary: + // see dojo.map(). The primary difference is that the acted-on + // array is implicitly this NodeList and the return is a + // dojo.NodeList (a subclass of Array) + ///return d.map(this, func, obj, d.NodeList); // dojo.NodeList + return tnl(d.map(this, func, obj)); // dojo.NodeList + }, + + forEach: function(callback, thisObj){ + // summary: + // see `dojo.forEach()`. The primary difference is that the acted-on + // array is implicitly this NodeList + d.forEach(this, callback, thisObj); + // non-standard return to allow easier chaining + return this; // dojo.NodeList + }, + + + /*===== + coords: function(){ + // summary: + // Returns the box objects all elements in a node list as + // an Array (*not* a NodeList) + + return d.map(this, d.coords); // Array + }, + + attr: function(property, value){ + // summary: + // gets or sets the DOM attribute for every element in the + // NodeList + // property: String + // the attribute to get/set + // value: String? + // optional. The value to set the property to + // returns: + // if no value is passed, the result is an array of attribute values + // If a value is passed, the return is this NodeList + return; // dojo.NodeList + return; // Array + }, + + style: function(property, value){ + // summary: + // gets or sets the CSS property for every element in the NodeList + // property: String + // the CSS property to get/set, in JavaScript notation + // ("lineHieght" instead of "line-height") + // value: String? + // optional. The value to set the property to + // returns: + // if no value is passed, the result is an array of strings. + // If a value is passed, the return is this NodeList + return; // dojo.NodeList + return; // Array + }, + + addClass: function(className){ + // summary: + // adds the specified class to every node in the list + // className: String + // the CSS class to add + return; // dojo.NodeList + }, + + removeClass: function(className){ + // summary: + // removes the specified class from every node in the list + // className: String + // the CSS class to add + // returns: + // dojo.NodeList, this list + return; // dojo.NodeList + }, + + toggleClass: function(className, condition){ + // summary: + // Adds a class to node if not present, or removes if present. + // Pass a boolean condition if you want to explicitly add or remove. + // condition: Boolean? + // If passed, true means to add the class, false means to remove. + // className: String + // the CSS class to add + return; // dojo.NodeList + }, + + connect: function(methodName, objOrFunc, funcName){ + // summary: + // attach event handlers to every item of the NodeList. Uses dojo.connect() + // so event properties are normalized + // methodName: String + // the name of the method to attach to. For DOM events, this should be + // the lower-case name of the event + // objOrFunc: Object|Function|String + // if 2 arguments are passed (methodName, objOrFunc), objOrFunc should + // reference a function or be the name of the function in the global + // namespace to attach. If 3 arguments are provided + // (methodName, objOrFunc, funcName), objOrFunc must be the scope to + // locate the bound function in + // funcName: String? + // optional. A string naming the function in objOrFunc to bind to the + // event. May also be a function reference. + // example: + // add an onclick handler to every button on the page + // | dojo.query("div:nth-child(odd)").connect("onclick", function(e){ + // | + // | }); + // example: + // attach foo.bar() to every odd div's onmouseover + // | dojo.query("div:nth-child(odd)").connect("onmouseover", foo, "bar"); + }, + + empty: function(){ + // summary: + // clears all content from each node in the list. Effectively + // equivalent to removing all child nodes from every item in + // the list. + return this.forEach("item.innerHTML='';"); // dojo.NodeList + // FIXME: should we be checking for and/or disposing of widgets below these nodes? + }, + =====*/ + + // useful html methods + coords: adaptAsMap(d.coords), + + // FIXME: connectPublisher()? connectRunOnce()? + + /* + destroy: function(){ + // summary: + // destroys every item in the list. + this.forEach(d.destroy); + // FIXME: should we be checking for and/or disposing of widgets below these nodes? + }, + */ + + place: function(/*String||Node*/ queryOrNode, /*String*/ position){ + // summary: + // places elements of this node list relative to the first element matched + // by queryOrNode. Returns the original NodeList. See: `dojo.place` + // queryOrNode: + // may be a string representing any valid CSS3 selector or a DOM node. + // In the selector case, only the first matching element will be used + // for relative positioning. + // position: + // can be one of: + // | "last" (default) + // | "first" + // | "before" + // | "after" + // | "only" + // | "replace" + // or an offset in the childNodes property + var item = d.query(queryOrNode)[0]; + return this.forEach(function(node){ d.place(node, item, position); }); // dojo.NodeList + }, + + orphan: function(/*String?*/ simpleFilter){ + // summary: + // removes elements in this list that match the simple filter + // from their parents and returns them as a new NodeList. + // simpleFilter: + // single-expression CSS rule. For example, ".thinger" or + // "#someId[attrName='value']" but not "div > span". In short, + // anything which does not invoke a descent to evaluate but + // can instead be used to test a single node is acceptable. + // returns: + // `dojo.NodeList` containing the orpahned elements + return (simpleFilter ? d._filterQueryResult(this, simpleFilter) : this).forEach(orphan); // dojo.NodeList + }, + + adopt: function(/*String||Array||DomNode*/ queryOrListOrNode, /*String?*/ position){ + // summary: + // places any/all elements in queryOrListOrNode at a + // position relative to the first element in this list. + // Returns a dojo.NodeList of the adopted elements. + // queryOrListOrNode: + // a DOM node or a query string or a query result. + // Represents the nodes to be adopted relative to the + // first element of this NodeList. + // position: + // can be one of: + // | "last" (default) + // | "first" + // | "before" + // | "after" + // | "only" + // | "replace" + // or an offset in the childNodes property + return d.query(queryOrListOrNode).place(item[0], position); // dojo.NodeList + }, + + // FIXME: do we need this? + query: function(/*String*/ queryStr){ + // summary: + // Returns a new list whose memebers match the passed query, + // assuming elements of the current NodeList as the root for + // each search. + // example: + // assume a DOM created by this markup: + // | <div id="foo"> + // | <p> + // | bacon is tasty, <span>dontcha think?</span> + // | </p> + // | </div> + // | <div id="bar"> + // | <p>great commedians may not be funny <span>in person</span></p> + // | </div> + // If we are presented with the following defintion for a NodeList: + // | var l = new dojo.NodeList(dojo.byId("foo"), dojo.byId("bar")); + // it's possible to find all span elements under paragraphs + // contained by these elements with this sub-query: + // | var spans = l.query("p span"); + + // FIXME: probably slow + if(!queryStr){ return this; } + var ret = this.map(function(node){ + // FIXME: why would we ever get undefined here? + return d.query(queryStr, node).filter(function(subNode){ return subNode !== undefined; }); + }); + return tnl(apc.apply([], ret)); // dojo.NodeList + }, + + filter: function(/*String|Function*/ simpleFilter){ + // summary: + // "masks" the built-in javascript filter() method (supported + // in Dojo via `dojo.filter`) to support passing a simple + // string filter in addition to supporting filtering function + // objects. + // simpleFilter: + // If a string, a single-expression CSS rule. For example, + // ".thinger" or "#someId[attrName='value']" but not "div > + // span". In short, anything which does not invoke a descent + // to evaluate but can instead be used to test a single node + // is acceptable. + // example: + // "regular" JS filter syntax as exposed in dojo.filter: + // | dojo.query("*").filter(function(item){ + // | // highlight every paragraph + // | return (item.nodeName == "p"); + // | }).style("backgroundColor", "yellow"); + // example: + // the same filtering using a CSS selector + // | dojo.query("*").filter("p").styles("backgroundColor", "yellow"); + + var a = arguments, items = this, start = 0; + if(d.isString(simpleFilter)){ + items = d._filterQueryResult(this, a[0]); + if(a.length == 1){ + // if we only got a string query, pass back the filtered results + return items; // dojo.NodeList + } + // if we got a callback, run it over the filtered items + start = 1; + } + return tnl(d.filter(items, a[start], a[start + 1])); // dojo.NodeList + }, + + /* + // FIXME: should this be "copyTo" and include parenting info? + clone: function(){ + // summary: + // creates node clones of each element of this list + // and returns a new list containing the clones + }, + */ + + addContent: function(/*String|DomNode*/ content, /*String||Integer?*/ position){ + // summary: + // add a node or some HTML as a string to every item in the + // list. Returns the original list. + // description: + // a copy of the HTML content is added to each item in the + // list, with an optional position argument. If no position + // argument is provided, the content is appended to the end of + // each item. + // content: + // DOM node or HTML in string format to add at position to + // every item + // position: + // can be one of: + // | "last"||"end" (default) + // | "first||"start" + // | "before" + // | "after" + // or an offset in the childNodes property + // example: + // appends content to the end if the position is ommitted + // | dojo.query("h3 > p").addContent("hey there!"); + // example: + // add something to the front of each element that has a + // "thinger" property: + // | dojo.query("[thinger]").addContent("...", "first"); + // example: + // adds a header before each element of the list + // | dojo.query(".note").addContent("<h4>NOTE:</h4>", "before"); + // example: + // add a clone of a DOM node to the end of every element in + // the list, removing it from its existing parent. + // | dojo.query(".note").addContent(dojo.byId("foo")); + var c = d.isString(content) ? + d._toDom(content, this[0] && this[0].ownerDocument) : + content, + i, + l = this.length - 1; + for(i = 0; i < l; ++i){ + d.place(c.cloneNode(true), this[i], position); + } + if(l >= 0){ + d.place(c, this[l], position); + } + return this; // dojo.NodeList + }, + + instantiate: function(/*String|Object*/ declaredClass, /*Object?*/ properties){ + // summary: + // Create a new instance of a specified class, using the + // specified properties and each node in the nodeList as a + // srcNodeRef + var c = d.isFunction(declaredClass) ? declaredClass : d.getObject(declaredClass); + properties = properties || {}; + return this.forEach(function(node){ new c(properties, node); }); // dojo.NodeList + }, + + at: function(/*===== index =====*/){ + // summary: + // Returns a new NodeList comprised of items in this NodeList + // at the given index or indices. + // index: Integer... + // One or more 0-based indices of items in the current + // NodeList. + // returns: + // dojo.NodeList + var t = new dojo.NodeList(); + d.forEach(arguments, function(i){ if(this[i]){ t.push(this[i]); }}, this); + return t; // dojo.NodeList + } + + }); + + // syntactic sugar for DOM events + d.forEach([ + "blur", "focus", "change", "click", "error", "keydown", "keypress", + "keyup", "load", "mousedown", "mouseenter", "mouseleave", "mousemove", + "mouseout", "mouseover", "mouseup", "submit" + ], function(evt){ + var _oe = "on"+evt; + nlp[_oe] = function(a, b){ + return this.connect(_oe, a, b); + } + // FIXME: should these events trigger publishes? + /* + return (a ? this.connect(_oe, a, b) : + this.forEach(function(n){ + // FIXME: + // listeners get buried by + // addEventListener and can't be dug back + // out to be triggered externally. + // see: + // http://developer.mozilla.org/en/docs/DOM:element + + + + // FIXME: need synthetic event support! + var _e = { target: n, faux: true, type: evt }; + // dojo._event_listener._synthesizeEvent({}, { target: n, faux: true, type: evt }); + try{ n[evt](_e); }catch(e){ } + try{ n[_oe](_e); }catch(e){ } + }) + ); + } + */ + } + ); + +})(); + +} + +if(!dojo._hasResource["dojo._base.query"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.query"] = true; +if(typeof dojo != "undefined"){ + dojo.provide("dojo._base.query"); + + + +} + +/* + dojo.query() architectural overview: + + dojo.query is a relatively full-featured CSS3 query library. It is + designed to take any valid CSS3 selector and return the nodes matching + the selector. To do this quickly, it processes queries in several + steps, applying caching where profitable. + + The steps (roughly in reverse order of the way they appear in the code): + 1.) check to see if we already have a "query dispatcher" + - if so, use that with the given parameterization. Skip to step 4. + 2.) attempt to determine which branch to dispatch the query to: + - JS (optimized DOM iteration) + - native (FF3.1+, Safari 3.1+, IE 8+) + 3.) tokenize and convert to executable "query dispatcher" + - this is where the lion's share of the complexity in the + system lies. In the DOM version, the query dispatcher is + assembled as a chain of "yes/no" test functions pertaining to + a section of a simple query statement (".blah:nth-child(odd)" + but not "div div", which is 2 simple statements). Individual + statement dispatchers are cached (to prevent re-definition) + as are entire dispatch chains (to make re-execution of the + same query fast) + 4.) the resulting query dispatcher is called in the passed scope + (by default the top-level document) + - for DOM queries, this results in a recursive, top-down + evaluation of nodes based on each simple query section + - for native implementations, this may mean working around spec + bugs. So be it. + 5.) matched nodes are pruned to ensure they are unique (if necessary) +*/ + +;(function(d){ + // define everything in a closure for compressability reasons. "d" is an + // alias to "dojo" (or the toolkit alias object, e.g., "acme"). + + //////////////////////////////////////////////////////////////////////// + // Toolkit aliases + //////////////////////////////////////////////////////////////////////// + + // if you are extracing dojo.query for use in your own system, you will + // need to provide these methods and properties. No other porting should be + // necessary, save for configuring the system to use a class other than + // dojo.NodeList as the return instance instantiator + var trim = d.trim; + var each = d.forEach; + // d.isIE; // float + // d.isSafari; // float + // d.isOpera; // float + // d.isWebKit; // float + // d.doc ; // document element + var qlc = d._queryListCtor = d.NodeList; + var isString = d.isString; + + var getDoc = function(){ return d.doc; }; + var cssCaseBug = (d.isWebKit && ((getDoc().compatMode) == "BackCompat")); + + //////////////////////////////////////////////////////////////////////// + // Global utilities + //////////////////////////////////////////////////////////////////////// + + + // on browsers that support the "children" collection we can avoid a lot of + // iteration on chaff (non-element) nodes. + // why. + var childNodesName = !!getDoc().firstChild["children"] ? "children" : "childNodes"; + + var specials = ">~+"; + + // global thunk to determine whether we should treat the current query as + // case sensitive or not. This switch is flipped by the query evaluator + // based on the document passed as the context to search. + var caseSensitive = false; + + // how high? + var yesman = function(){ return true; }; + + //////////////////////////////////////////////////////////////////////// + // Tokenizer + //////////////////////////////////////////////////////////////////////// + + var getQueryParts = function(query){ + // summary: + // state machine for query tokenization + // description: + // instead of using a brittle and slow regex-based CSS parser, + // dojo.query implements an AST-style query representation. This + // representation is only generated once per query. For example, + // the same query run multiple times or under different root nodes + // does not re-parse the selector expression but instead uses the + // cached data structure. The state machine implemented here + // terminates on the last " " (space) charachter and returns an + // ordered array of query component structures (or "parts"). Each + // part represents an operator or a simple CSS filtering + // expression. The structure for parts is documented in the code + // below. + + + // NOTE: + // this code is designed to run fast and compress well. Sacrifices + // to readibility and maintainability have been made. Your best + // bet when hacking the tokenizer is to put The Donnas on *really* + // loud (may we recommend their "Spend The Night" release?) and + // just assume you're gonna make mistakes. Keep the unit tests + // open and run them frequently. Knowing is half the battle ;-) + if(specials.indexOf(query.slice(-1)) >= 0){ + // if we end with a ">", "+", or "~", that means we're implicitly + // searching all children, so make it explicit + query += " * " + }else{ + // if you have not provided a terminator, one will be provided for + // you... + query += " "; + } + + var ts = function(/*Integer*/ s, /*Integer*/ e){ + // trim and slice. + + // take an index to start a string slice from and an end position + // and return a trimmed copy of that sub-string + return trim(query.slice(s, e)); + } + + // the overall data graph of the full query, as represented by queryPart objects + var queryParts = []; + + + // state keeping vars + var inBrackets = -1, inParens = -1, inMatchFor = -1, + inPseudo = -1, inClass = -1, inId = -1, inTag = -1, + lc = "", cc = "", pStart; + + // iteration vars + var x = 0, // index in the query + ql = query.length, + currentPart = null, // data structure representing the entire clause + _cp = null; // the current pseudo or attr matcher + + // several temporary variables are assigned to this structure durring a + // potential sub-expression match: + // attr: + // a string representing the current full attribute match in a + // bracket expression + // type: + // if there's an operator in a bracket expression, this is + // used to keep track of it + // value: + // the internals of parenthetical expression for a pseudo. for + // :nth-child(2n+1), value might be "2n+1" + + var endTag = function(){ + // called when the tokenizer hits the end of a particular tag name. + // Re-sets state variables for tag matching and sets up the matcher + // to handle the next type of token (tag or operator). + if(inTag >= 0){ + var tv = (inTag == x) ? null : ts(inTag, x); // .toLowerCase(); + currentPart[ (specials.indexOf(tv) < 0) ? "tag" : "oper" ] = tv; + inTag = -1; + } + } + + var endId = function(){ + // called when the tokenizer might be at the end of an ID portion of a match + if(inId >= 0){ + currentPart.id = ts(inId, x).replace(/\\/g, ""); + inId = -1; + } + } + + var endClass = function(){ + // called when the tokenizer might be at the end of a class name + // match. CSS allows for multiple classes, so we augment the + // current item with another class in its list + if(inClass >= 0){ + currentPart.classes.push(ts(inClass+1, x).replace(/\\/g, "")); + inClass = -1; + } + } + + var endAll = function(){ + // at the end of a simple fragment, so wall off the matches + endId(); endTag(); endClass(); + } + + var endPart = function(){ + endAll(); + if(inPseudo >= 0){ + currentPart.pseudos.push({ name: ts(inPseudo+1, x) }); + } + // hint to the selector engine to tell it whether or not it + // needs to do any iteration. Many simple selectors don't, and + // we can avoid significant construction-time work by advising + // the system to skip them + currentPart.loops = ( + currentPart.pseudos.length || + currentPart.attrs.length || + currentPart.classes.length ); + + currentPart.oquery = currentPart.query = ts(pStart, x); // save the full expression as a string + + + // otag/tag are hints to suggest to the system whether or not + // it's an operator or a tag. We save a copy of otag since the + // tag name is cast to upper-case in regular HTML matches. The + // system has a global switch to figure out if the current + // expression needs to be case sensitive or not and it will use + // otag or tag accordingly + currentPart.otag = currentPart.tag = (currentPart["oper"]) ? null : (currentPart.tag || "*"); + + if(currentPart.tag){ + // if we're in a case-insensitive HTML doc, we likely want + // the toUpperCase when matching on element.tagName. If we + // do it here, we can skip the string op per node + // comparison + currentPart.tag = currentPart.tag.toUpperCase(); + } + + // add the part to the list + if(queryParts.length && (queryParts[queryParts.length-1].oper)){ + // operators are always infix, so we remove them from the + // list and attach them to the next match. The evaluator is + // responsible for sorting out how to handle them. + currentPart.infixOper = queryParts.pop(); + currentPart.query = currentPart.infixOper.query + " " + currentPart.query; + /* + + */ + } + queryParts.push(currentPart); + + currentPart = null; + } + + // iterate over the query, charachter by charachter, building up a + // list of query part objects + for(; lc=cc, cc=query.charAt(x), x < ql; x++){ + // cc: the current character in the match + // lc: the last charachter (if any) + + // someone is trying to escape something, so don't try to match any + // fragments. We assume we're inside a literal. + if(lc == "\\"){ continue; } + if(!currentPart){ // a part was just ended or none has yet been created + // NOTE: I hate all this alloc, but it's shorter than writing tons of if's + pStart = x; + // rules describe full CSS sub-expressions, like: + // #someId + // .className:first-child + // but not: + // thinger > div.howdy[type=thinger] + // the indidual components of the previous query would be + // split into 3 parts that would be represented a structure + // like: + // [ + // { + // query: "thinger", + // tag: "thinger", + // }, + // { + // query: "div.howdy[type=thinger]", + // classes: ["howdy"], + // infixOper: { + // query: ">", + // oper: ">", + // } + // }, + // ] + currentPart = { + query: null, // the full text of the part's rule + pseudos: [], // CSS supports multiple pseud-class matches in a single rule + attrs: [], // CSS supports multi-attribute match, so we need an array + classes: [], // class matches may be additive, e.g.: .thinger.blah.howdy + tag: null, // only one tag... + oper: null, // ...or operator per component. Note that these wind up being exclusive. + id: null, // the id component of a rule + getTag: function(){ + return (caseSensitive) ? this.otag : this.tag; + } + }; + + // if we don't have a part, we assume we're going to start at + // the beginning of a match, which should be a tag name. This + // might fault a little later on, but we detect that and this + // iteration will still be fine. + inTag = x; + } + + if(inBrackets >= 0){ + // look for a the close first + if(cc == "]"){ // if we're in a [...] clause and we end, do assignment + if(!_cp.attr){ + // no attribute match was previously begun, so we + // assume this is an attribute existance match in the + // form of [someAttributeName] + _cp.attr = ts(inBrackets+1, x); + }else{ + // we had an attribute already, so we know that we're + // matching some sort of value, as in [attrName=howdy] + _cp.matchFor = ts((inMatchFor||inBrackets+1), x); + } + var cmf = _cp.matchFor; + if(cmf){ + // try to strip quotes from the matchFor value. We want + // [attrName=howdy] to match the same + // as [attrName = 'howdy' ] + if( (cmf.charAt(0) == '"') || (cmf.charAt(0) == "'") ){ + _cp.matchFor = cmf.slice(1, -1); + } + } + // end the attribute by adding it to the list of attributes. + currentPart.attrs.push(_cp); + _cp = null; // necessary? + inBrackets = inMatchFor = -1; + }else if(cc == "="){ + // if the last char was an operator prefix, make sure we + // record it along with the "=" operator. + var addToCc = ("|~^$*".indexOf(lc) >=0 ) ? lc : ""; + _cp.type = addToCc+cc; + _cp.attr = ts(inBrackets+1, x-addToCc.length); + inMatchFor = x+1; + } + // now look for other clause parts + }else if(inParens >= 0){ + // if we're in a parenthetical expression, we need to figure + // out if it's attached to a pseduo-selector rule like + // :nth-child(1) + if(cc == ")"){ + if(inPseudo >= 0){ + _cp.value = ts(inParens+1, x); + } + inPseudo = inParens = -1; + } + }else if(cc == "#"){ + // start of an ID match + endAll(); + inId = x+1; + }else if(cc == "."){ + // start of a class match + endAll(); + inClass = x; + }else if(cc == ":"){ + // start of a pseudo-selector match + endAll(); + inPseudo = x; + }else if(cc == "["){ + // start of an attribute match. + endAll(); + inBrackets = x; + // provide a new structure for the attribute match to fill-in + _cp = { + /*===== + attr: null, type: null, matchFor: null + =====*/ + }; + }else if(cc == "("){ + // we really only care if we've entered a parenthetical + // expression if we're already inside a pseudo-selector match + if(inPseudo >= 0){ + // provide a new structure for the pseudo match to fill-in + _cp = { + name: ts(inPseudo+1, x), + value: null + } + currentPart.pseudos.push(_cp); + } + inParens = x; + }else if( + (cc == " ") && + // if it's a space char and the last char is too, consume the + // current one without doing more work + (lc != cc) + ){ + endPart(); + } + } + return queryParts; + }; + + + //////////////////////////////////////////////////////////////////////// + // DOM query infrastructure + //////////////////////////////////////////////////////////////////////// + + var agree = function(first, second){ + // the basic building block of the yes/no chaining system. agree(f1, + // f2) generates a new function which returns the boolean results of + // both of the passed functions to a single logical-anded result. If + // either are not possed, the other is used exclusively. + if(!first){ return second; } + if(!second){ return first; } + + return function(){ + return first.apply(window, arguments) && second.apply(window, arguments); + } + }; + + var getArr = function(i, arr){ + // helps us avoid array alloc when we don't need it + var r = arr||[]; // FIXME: should this be 'new d._queryListCtor()' ? + if(i){ r.push(i); } + return r; + }; + + var _isElement = function(n){ return (1 == n.nodeType); }; + + // FIXME: need to coalesce _getAttr with defaultGetter + var blank = ""; + var _getAttr = function(elem, attr){ + if(!elem){ return blank; } + if(attr == "class"){ + return elem.className || blank; + } + if(attr == "for"){ + return elem.htmlFor || blank; + } + if(attr == "style"){ + return elem.style.cssText || blank; + } + return (caseSensitive ? elem.getAttribute(attr) : elem.getAttribute(attr, 2)) || blank; + }; + + var attrs = { + "*=": function(attr, value){ + return function(elem){ + // E[foo*="bar"] + // an E element whose "foo" attribute value contains + // the substring "bar" + return (_getAttr(elem, attr).indexOf(value)>=0); + } + }, + "^=": function(attr, value){ + // E[foo^="bar"] + // an E element whose "foo" attribute value begins exactly + // with the string "bar" + return function(elem){ + return (_getAttr(elem, attr).indexOf(value)==0); + } + }, + "$=": function(attr, value){ + // E[foo$="bar"] + // an E element whose "foo" attribute value ends exactly + // with the string "bar" + var tval = " "+value; + return function(elem){ + var ea = " "+_getAttr(elem, attr); + return (ea.lastIndexOf(value)==(ea.length-value.length)); + } + }, + "~=": function(attr, value){ + // E[foo~="bar"] + // an E element whose "foo" attribute value is a list of + // space-separated values, one of which is exactly equal + // to "bar" + + // return "[contains(concat(' ',@"+attr+",' '), ' "+ value +" ')]"; + var tval = " "+value+" "; + return function(elem){ + var ea = " "+_getAttr(elem, attr)+" "; + return (ea.indexOf(tval)>=0); + } + }, + "|=": function(attr, value){ + // E[hreflang|="en"] + // an E element whose "hreflang" attribute has a + // hyphen-separated list of values beginning (from the + // left) with "en" + var valueDash = " "+value+"-"; + return function(elem){ + var ea = " "+_getAttr(elem, attr); + return ( + (ea == value) || + (ea.indexOf(valueDash)==0) + ); + } + }, + "=": function(attr, value){ + return function(elem){ + return (_getAttr(elem, attr) == value); + } + } + }; + + // avoid testing for node type if we can. Defining this in the negative + // here to avoid negation in the fast path. + var _noNES = (typeof getDoc().firstChild.nextElementSibling == "undefined"); + var _ns = !_noNES ? "nextElementSibling" : "nextSibling"; + var _ps = !_noNES ? "previousElementSibling" : "previousSibling"; + var _simpleNodeTest = (_noNES ? _isElement : yesman); + + var _lookLeft = function(node){ + // look left + while(node = node[_ps]){ + if(_simpleNodeTest(node)){ return false; } + } + return true; + }; + + var _lookRight = function(node){ + // look right + while(node = node[_ns]){ + if(_simpleNodeTest(node)){ return false; } + } + return true; + }; + + var getNodeIndex = function(node){ + var root = node.parentNode; + var i = 0, + tret = root[childNodesName], + ci = (node["_i"]||-1), + cl = (root["_l"]||-1); + + if(!tret){ return -1; } + var l = tret.length; + + // we calcuate the parent length as a cheap way to invalidate the + // cache. It's not 100% accurate, but it's much more honest than what + // other libraries do + if( cl == l && ci >= 0 && cl >= 0 ){ + // if it's legit, tag and release + return ci; + } + + // else re-key things + root["_l"] = l; + ci = -1; + for(var te = root["firstElementChild"]||root["firstChild"]; te; te = te[_ns]){ + if(_simpleNodeTest(te)){ + te["_i"] = ++i; + if(node === te){ + // NOTE: + // shortcuting the return at this step in indexing works + // very well for benchmarking but we avoid it here since + // it leads to potential O(n^2) behavior in sequential + // getNodexIndex operations on a previously un-indexed + // parent. We may revisit this at a later time, but for + // now we just want to get the right answer more often + // than not. + ci = i; + } + } + } + return ci; + }; + + var isEven = function(elem){ + return !((getNodeIndex(elem)) % 2); + }; + + var isOdd = function(elem){ + return ((getNodeIndex(elem)) % 2); + }; + + var pseudos = { + "checked": function(name, condition){ + return function(elem){ + // FIXME: make this more portable!! + return !!d.attr(elem, "checked"); + } + }, + "first-child": function(){ return _lookLeft; }, + "last-child": function(){ return _lookRight; }, + "only-child": function(name, condition){ + return function(node){ + if(!_lookLeft(node)){ return false; } + if(!_lookRight(node)){ return false; } + return true; + }; + }, + "empty": function(name, condition){ + return function(elem){ + // DomQuery and jQuery get this wrong, oddly enough. + // The CSS 3 selectors spec is pretty explicit about it, too. + var cn = elem.childNodes; + var cnl = elem.childNodes.length; + // if(!cnl){ return true; } + for(var x=cnl-1; x >= 0; x--){ + var nt = cn[x].nodeType; + if((nt === 1)||(nt == 3)){ return false; } + } + return true; + } + }, + "contains": function(name, condition){ + var cz = condition.charAt(0); + if( cz == '"' || cz == "'" ){ //remove quote + condition = condition.slice(1, -1); + } + return function(elem){ + return (elem.innerHTML.indexOf(condition) >= 0); + } + }, + "not": function(name, condition){ + var p = getQueryParts(condition)[0]; + var ignores = { el: 1 }; + if(p.tag != "*"){ + ignores.tag = 1; + } + if(!p.classes.length){ + ignores.classes = 1; + } + var ntf = getSimpleFilterFunc(p, ignores); + return function(elem){ + return (!ntf(elem)); + } + }, + "nth-child": function(name, condition){ + var pi = parseInt; + // avoid re-defining function objects if we can + if(condition == "odd"){ + return isOdd; + }else if(condition == "even"){ + return isEven; + } + // FIXME: can we shorten this? + if(condition.indexOf("n") != -1){ + var tparts = condition.split("n", 2); + var pred = tparts[0] ? ((tparts[0] == '-') ? -1 : pi(tparts[0])) : 1; + var idx = tparts[1] ? pi(tparts[1]) : 0; + var lb = 0, ub = -1; + if(pred > 0){ + if(idx < 0){ + idx = (idx % pred) && (pred + (idx % pred)); + }else if(idx>0){ + if(idx >= pred){ + lb = idx - idx % pred; + } + idx = idx % pred; + } + }else if(pred<0){ + pred *= -1; + // idx has to be greater than 0 when pred is negative; + // shall we throw an error here? + if(idx > 0){ + ub = idx; + idx = idx % pred; + } + } + if(pred > 0){ + return function(elem){ + var i = getNodeIndex(elem); + return (i>=lb) && (ub<0 || i<=ub) && ((i % pred) == idx); + } + }else{ + condition = idx; + } + } + var ncount = pi(condition); + return function(elem){ + return (getNodeIndex(elem) == ncount); + } + } + }; + + var defaultGetter = (d.isIE) ? function(cond){ + var clc = cond.toLowerCase(); + if(clc == "class"){ cond = "className"; } + return function(elem){ + return (caseSensitive ? elem.getAttribute(cond) : elem[cond]||elem[clc]); + } + } : function(cond){ + return function(elem){ + return (elem && elem.getAttribute && elem.hasAttribute(cond)); + } + }; + + var getSimpleFilterFunc = function(query, ignores){ + // generates a node tester function based on the passed query part. The + // query part is one of the structures generatd by the query parser + // when it creates the query AST. The "ignores" object specifies which + // (if any) tests to skip, allowing the system to avoid duplicating + // work where it may have already been taken into account by other + // factors such as how the nodes to test were fetched in the first + // place + if(!query){ return yesman; } + ignores = ignores||{}; + + var ff = null; + + if(!("el" in ignores)){ + ff = agree(ff, _isElement); + } + + if(!("tag" in ignores)){ + if(query.tag != "*"){ + ff = agree(ff, function(elem){ + return (elem && (elem.tagName == query.getTag())); + }); + } + } + + if(!("classes" in ignores)){ + each(query.classes, function(cname, idx, arr){ + // get the class name + /* + var isWildcard = cname.charAt(cname.length-1) == "*"; + if(isWildcard){ + cname = cname.substr(0, cname.length-1); + } + // I dislike the regex thing, even if memozied in a cache, but it's VERY short + var re = new RegExp("(?:^|\\s)" + cname + (isWildcard ? ".*" : "") + "(?:\\s|$)"); + */ + var re = new RegExp("(?:^|\\s)" + cname + "(?:\\s|$)"); + ff = agree(ff, function(elem){ + return re.test(elem.className); + }); + ff.count = idx; + }); + } + + if(!("pseudos" in ignores)){ + each(query.pseudos, function(pseudo){ + var pn = pseudo.name; + if(pseudos[pn]){ + ff = agree(ff, pseudos[pn](pn, pseudo.value)); + } + }); + } + + if(!("attrs" in ignores)){ + each(query.attrs, function(attr){ + var matcher; + var a = attr.attr; + // type, attr, matchFor + if(attr.type && attrs[attr.type]){ + matcher = attrs[attr.type](a, attr.matchFor); + }else if(a.length){ + matcher = defaultGetter(a); + } + if(matcher){ + ff = agree(ff, matcher); + } + }); + } + + if(!("id" in ignores)){ + if(query.id){ + ff = agree(ff, function(elem){ + return (!!elem && (elem.id == query.id)); + }); + } + } + + if(!ff){ + if(!("default" in ignores)){ + ff = yesman; + } + } + return ff; + }; + + var _nextSibling = function(filterFunc){ + return function(node, ret, bag){ + while(node = node[_ns]){ + if(_noNES && (!_isElement(node))){ continue; } + if( + (!bag || _isUnique(node, bag)) && + filterFunc(node) + ){ + ret.push(node); + } + break; + } + return ret; + } + }; + + var _nextSiblings = function(filterFunc){ + return function(root, ret, bag){ + var te = root[_ns]; + while(te){ + if(_simpleNodeTest(te)){ + if(bag && !_isUnique(te, bag)){ + break; + } + if(filterFunc(te)){ + ret.push(te); + } + } + te = te[_ns]; + } + return ret; + } + }; + + // get an array of child *elements*, skipping text and comment nodes + var _childElements = function(filterFunc){ + filterFunc = filterFunc||yesman; + return function(root, ret, bag){ + // get an array of child elements, skipping text and comment nodes + var te, x = 0, tret = root[childNodesName]; + while(te = tret[x++]){ + if( + _simpleNodeTest(te) && + (!bag || _isUnique(te, bag)) && + (filterFunc(te, x)) + ){ + ret.push(te); + } + } + return ret; + }; + }; + + /* + // thanks, Dean! + var itemIsAfterRoot = d.isIE ? function(item, root){ + return (item.sourceIndex > root.sourceIndex); + } : function(item, root){ + return (item.compareDocumentPosition(root) == 2); + }; + */ + + // test to see if node is below root + var _isDescendant = function(node, root){ + var pn = node.parentNode; + while(pn){ + if(pn == root){ + break; + } + pn = pn.parentNode; + } + return !!pn; + }; + + var _getElementsFuncCache = {}; + + var getElementsFunc = function(query){ + var retFunc = _getElementsFuncCache[query.query]; + // if we've got a cached dispatcher, just use that + if(retFunc){ return retFunc; } + // else, generate a new on + + // NOTE: + // this function returns a function that searches for nodes and + // filters them. The search may be specialized by infix operators + // (">", "~", or "+") else it will default to searching all + // descendants (the " " selector). Once a group of children is + // founde, a test function is applied to weed out the ones we + // don't want. Many common cases can be fast-pathed. We spend a + // lot of cycles to create a dispatcher that doesn't do more work + // than necessary at any point since, unlike this function, the + // dispatchers will be called every time. The logic of generating + // efficient dispatchers looks like this in pseudo code: + // + // # if it's a purely descendant query (no ">", "+", or "~" modifiers) + // if infixOperator == " ": + // if only(id): + // return def(root): + // return d.byId(id, root); + // + // elif id: + // return def(root): + // return filter(d.byId(id, root)); + // + // elif cssClass && getElementsByClassName: + // return def(root): + // return filter(root.getElementsByClassName(cssClass)); + // + // elif only(tag): + // return def(root): + // return root.getElementsByTagName(tagName); + // + // else: + // # search by tag name, then filter + // return def(root): + // return filter(root.getElementsByTagName(tagName||"*")); + // + // elif infixOperator == ">": + // # search direct children + // return def(root): + // return filter(root.children); + // + // elif infixOperator == "+": + // # search next sibling + // return def(root): + // return filter(root.nextElementSibling); + // + // elif infixOperator == "~": + // # search rightward siblings + // return def(root): + // return filter(nextSiblings(root)); + + var io = query.infixOper; + var oper = (io ? io.oper : ""); + // the default filter func which tests for all conditions in the query + // part. This is potentially inefficient, so some optimized paths may + // re-define it to test fewer things. + var filterFunc = getSimpleFilterFunc(query, { el: 1 }); + var qt = query.tag; + var wildcardTag = ("*" == qt); + var ecs = getDoc()["getElementsByClassName"]; + + if(!oper){ + // if there's no infix operator, then it's a descendant query. ID + // and "elements by class name" variants can be accelerated so we + // call them out explicitly: + if(query.id){ + // testing shows that the overhead of yesman() is acceptable + // and can save us some bytes vs. re-defining the function + // everywhere. + filterFunc = (!query.loops && wildcardTag) ? + yesman : + getSimpleFilterFunc(query, { el: 1, id: 1 }); + + retFunc = function(root, arr){ + var te = d.byId(query.id, (root.ownerDocument||root)); + if(!te || !filterFunc(te)){ return; } + if(9 == root.nodeType){ // if root's a doc, we just return directly + return getArr(te, arr); + }else{ // otherwise check ancestry + if(_isDescendant(te, root)){ + return getArr(te, arr); + } + } + } + }else if( + ecs && + // isAlien check. Workaround for Prototype.js being totally evil/dumb. + /\{\s*\[native code\]\s*\}/.test(String(ecs)) && + query.classes.length && + // WebKit bug where quirks-mode docs select by class w/o case sensitivity + !cssCaseBug + ){ + // it's a class-based query and we've got a fast way to run it. + + // ignore class and ID filters since we will have handled both + filterFunc = getSimpleFilterFunc(query, { el: 1, classes: 1, id: 1 }); + var classesString = query.classes.join(" "); + retFunc = function(root, arr, bag){ + var ret = getArr(0, arr), te, x=0; + var tret = root.getElementsByClassName(classesString); + while((te = tret[x++])){ + if(filterFunc(te, root) && _isUnique(te, bag)){ + ret.push(te); + } + } + return ret; + }; + + }else if(!wildcardTag && !query.loops){ + // it's tag only. Fast-path it. + retFunc = function(root, arr, bag){ + var ret = getArr(0, arr), te, x=0; + var tret = root.getElementsByTagName(query.getTag()); + while((te = tret[x++])){ + if(_isUnique(te, bag)){ + ret.push(te); + } + } + return ret; + }; + }else{ + // the common case: + // a descendant selector without a fast path. By now it's got + // to have a tag selector, even if it's just "*" so we query + // by that and filter + filterFunc = getSimpleFilterFunc(query, { el: 1, tag: 1, id: 1 }); + retFunc = function(root, arr, bag){ + var ret = getArr(0, arr), te, x=0; + // we use getTag() to avoid case sensitivity issues + var tret = root.getElementsByTagName(query.getTag()); + while((te = tret[x++])){ + if(filterFunc(te, root) && _isUnique(te, bag)){ + ret.push(te); + } + } + return ret; + }; + } + }else{ + // the query is scoped in some way. Instead of querying by tag we + // use some other collection to find candidate nodes + var skipFilters = { el: 1 }; + if(wildcardTag){ + skipFilters.tag = 1; + } + filterFunc = getSimpleFilterFunc(query, skipFilters); + if("+" == oper){ + retFunc = _nextSibling(filterFunc); + }else if("~" == oper){ + retFunc = _nextSiblings(filterFunc); + }else if(">" == oper){ + retFunc = _childElements(filterFunc); + } + } + // cache it and return + return _getElementsFuncCache[query.query] = retFunc; + }; + + var filterDown = function(root, queryParts){ + // NOTE: + // this is the guts of the DOM query system. It takes a list of + // parsed query parts and a root and finds children which match + // the selector represented by the parts + var candidates = getArr(root), qp, x, te, qpl = queryParts.length, bag, ret; + + for(var i = 0; i < qpl; i++){ + ret = []; + qp = queryParts[i]; + x = candidates.length - 1; + if(x > 0){ + // if we have more than one root at this level, provide a new + // hash to use for checking group membership but tell the + // system not to post-filter us since we will already have been + // gauranteed to be unique + bag = {}; + ret.nozip = true; + } + var gef = getElementsFunc(qp); + while(te = candidates[x--]){ + // for every root, get the elements that match the descendant + // selector, adding them to the "ret" array and filtering them + // via membership in this level's bag. If there are more query + // parts, then this level's return will be used as the next + // level's candidates + gef(te, ret, bag); + } + if(!ret.length){ break; } + candidates = ret; + } + return ret; + }; + + //////////////////////////////////////////////////////////////////////// + // the query runner + //////////////////////////////////////////////////////////////////////// + + // these are the primary caches for full-query results. The query + // dispatcher functions are generated then stored here for hash lookup in + // the future + var _queryFuncCacheDOM = {}, + _queryFuncCacheQSA = {}; + + // this is the second level of spliting, from full-length queries (e.g., + // "div.foo .bar") into simple query expressions (e.g., ["div.foo", + // ".bar"]) + var getStepQueryFunc = function(query){ + var qparts = getQueryParts(trim(query)); + + // if it's trivial, avoid iteration and zipping costs + if(qparts.length == 1){ + // we optimize this case here to prevent dispatch further down the + // chain, potentially slowing things down. We could more elegantly + // handle this in filterDown(), but it's slower for simple things + // that need to be fast (e.g., "#someId"). + var tef = getElementsFunc(qparts[0]); + return function(root){ + var r = tef(root, new qlc()); + if(r){ r.nozip = true; } + return r; + } + } + + // otherwise, break it up and return a runner that iterates over the parts recursively + return function(root){ + return filterDown(root, qparts); + } + }; + + // NOTES: + // * we can't trust QSA for anything but document-rooted queries, so + // caching is split into DOM query evaluators and QSA query evaluators + // * caching query results is dirty and leak-prone (or, at a minimum, + // prone to unbounded growth). Other toolkits may go this route, but + // they totally destroy their own ability to manage their memory + // footprint. If we implement it, it should only ever be with a fixed + // total element reference # limit and an LRU-style algorithm since JS + // has no weakref support. Caching compiled query evaluators is also + // potentially problematic, but even on large documents the size of the + // query evaluators is often < 100 function objects per evaluator (and + // LRU can be applied if it's ever shown to be an issue). + // * since IE's QSA support is currently only for HTML documents and even + // then only in IE 8's "standards mode", we have to detect our dispatch + // route at query time and keep 2 separate caches. Ugg. + + // we need to determine if we think we can run a given query via + // querySelectorAll or if we'll need to fall back on DOM queries to get + // there. We need a lot of information about the environment and the query + // to make the determiniation (e.g. does it support QSA, does the query in + // question work in the native QSA impl, etc.). + var nua = navigator.userAgent; + // some versions of Safari provided QSA, but it was buggy and crash-prone. + // We need te detect the right "internal" webkit version to make this work. + var wk = "WebKit/"; + var is525 = ( + d.isWebKit && + (nua.indexOf(wk) > 0) && + (parseFloat(nua.split(wk)[1]) > 528) + ); + + // IE QSA queries may incorrectly include comment nodes, so we throw the + // zipping function into "remove" comments mode instead of the normal "skip + // it" which every other QSA-clued browser enjoys + var noZip = d.isIE ? "commentStrip" : "nozip"; + + var qsa = "querySelectorAll"; + var qsaAvail = ( + !!getDoc()[qsa] && + // see #5832 + (!d.isSafari || (d.isSafari > 3.1) || is525 ) + ); + var getQueryFunc = function(query, forceDOM){ + + if(qsaAvail){ + // if we've got a cached variant and we think we can do it, run it! + var qsaCached = _queryFuncCacheQSA[query]; + if(qsaCached && !forceDOM){ return qsaCached; } + } + + // else if we've got a DOM cached variant, assume that we already know + // all we need to and use it + var domCached = _queryFuncCacheDOM[query]; + if(domCached){ return domCached; } + + // TODO: + // today we're caching DOM and QSA branches separately so we + // recalc useQSA every time. If we had a way to tag root+query + // efficiently, we'd be in good shape to do a global cache. + + var qcz = query.charAt(0); + var nospace = (-1 == query.indexOf(" ")); + + // byId searches are wicked fast compared to QSA, even when filtering + // is required + if( (query.indexOf("#") >= 0) && (nospace) ){ + forceDOM = true; + } + + var useQSA = ( + qsaAvail && (!forceDOM) && + // as per CSS 3, we can't currently start w/ combinator: + // http://www.w3.org/TR/css3-selectors/#w3cselgrammar + (specials.indexOf(qcz) == -1) && + // IE's QSA impl sucks on pseudos + (!d.isIE || (query.indexOf(":") == -1)) && + + (!(cssCaseBug && (query.indexOf(".") >= 0))) && + + // FIXME: + // need to tighten up browser rules on ":contains" and "|=" to + // figure out which aren't good + (query.indexOf(":contains") == -1) && + (query.indexOf("|=") == -1) // some browsers don't grok it + ); + + // TODO: + // if we've got a descendant query (e.g., "> .thinger" instead of + // just ".thinger") in a QSA-able doc, but are passed a child as a + // root, it should be possible to give the item a synthetic ID and + // trivially rewrite the query to the form "#synid > .thinger" to + // use the QSA branch + + + if(useQSA){ + var tq = (specials.indexOf(query.charAt(query.length-1)) >= 0) ? + (query + " *") : query; + return _queryFuncCacheQSA[query] = function(root){ + try{ + // the QSA system contains an egregious spec bug which + // limits us, effectively, to only running QSA queries over + // entire documents. See: + // http://ejohn.org/blog/thoughts-on-queryselectorall/ + // despite this, we can also handle QSA runs on simple + // selectors, but we don't want detection to be expensive + // so we're just checking for the presence of a space char + // right now. Not elegant, but it's cheaper than running + // the query parser when we might not need to + if(!((9 == root.nodeType) || nospace)){ throw ""; } + var r = root[qsa](tq); + // skip expensive duplication checks and just wrap in a NodeList + r[noZip] = true; + return r; + }catch(e){ + // else run the DOM branch on this query, ensuring that we + // default that way in the future + return getQueryFunc(query, true)(root); + } + } + }else{ + // DOM branch + var parts = query.split(/\s*,\s*/); + return _queryFuncCacheDOM[query] = ((parts.length < 2) ? + // if not a compound query (e.g., ".foo, .bar"), cache and return a dispatcher + getStepQueryFunc(query) : + // if it *is* a complex query, break it up into its + // constituent parts and return a dispatcher that will + // merge the parts when run + function(root){ + var pindex = 0, // avoid array alloc for every invocation + ret = [], + tp; + while((tp = parts[pindex++])){ + ret = ret.concat(getStepQueryFunc(tp)(root)); + } + return ret; + } + ); + } + }; + + var _zipIdx = 0; + + // NOTE: + // this function is Moo inspired, but our own impl to deal correctly + // with XML in IE + var _nodeUID = d.isIE ? function(node){ + if(caseSensitive){ + // XML docs don't have uniqueID on their nodes + return (node.getAttribute("_uid") || node.setAttribute("_uid", ++_zipIdx) || _zipIdx); + + }else{ + return node.uniqueID; + } + } : + function(node){ + return (node._uid || (node._uid = ++_zipIdx)); + }; + + // determine if a node in is unique in a "bag". In this case we don't want + // to flatten a list of unique items, but rather just tell if the item in + // question is already in the bag. Normally we'd just use hash lookup to do + // this for us but IE's DOM is busted so we can't really count on that. On + // the upside, it gives us a built in unique ID function. + var _isUnique = function(node, bag){ + if(!bag){ return 1; } + var id = _nodeUID(node); + if(!bag[id]){ return bag[id] = 1; } + return 0; + }; + + // attempt to efficiently determine if an item in a list is a dupe, + // returning a list of "uniques", hopefully in doucment order + var _zipIdxName = "_zipIdx"; + var _zip = function(arr){ + if(arr && arr.nozip){ + return (qlc._wrap) ? qlc._wrap(arr) : arr; + } + // var ret = new d._queryListCtor(); + var ret = new qlc(); + if(!arr || !arr.length){ return ret; } + if(arr[0]){ + ret.push(arr[0]); + } + if(arr.length < 2){ return ret; } + + _zipIdx++; + + // we have to fork here for IE and XML docs because we can't set + // expandos on their nodes (apparently). *sigh* + if(d.isIE && caseSensitive){ + var szidx = _zipIdx+""; + arr[0].setAttribute(_zipIdxName, szidx); + for(var x = 1, te; te = arr[x]; x++){ + if(arr[x].getAttribute(_zipIdxName) != szidx){ + ret.push(te); + } + te.setAttribute(_zipIdxName, szidx); + } + }else if(d.isIE && arr.commentStrip){ + try{ + for(var x = 1, te; te = arr[x]; x++){ + if(_isElement(te)){ + ret.push(te); + } + } + }catch(e){ /* squelch */ } + }else{ + if(arr[0]){ arr[0][_zipIdxName] = _zipIdx; } + for(var x = 1, te; te = arr[x]; x++){ + if(arr[x][_zipIdxName] != _zipIdx){ + ret.push(te); + } + te[_zipIdxName] = _zipIdx; + } + } + return ret; + }; + + // the main executor + d.query = function(/*String*/ query, /*String|DOMNode?*/ root){ + // summary: + // Returns nodes which match the given CSS3 selector, searching the + // entire document by default but optionally taking a node to scope + // the search by. Returns an instance of dojo.NodeList. + // description: + // dojo.query() is the swiss army knife of DOM node manipulation in + // Dojo. Much like Prototype's "$$" (bling-bling) function or JQuery's + // "$" function, dojo.query provides robust, high-performance + // CSS-based node selector support with the option of scoping searches + // to a particular sub-tree of a document. + // + // Supported Selectors: + // -------------------- + // + // dojo.query() supports a rich set of CSS3 selectors, including: + // + // * class selectors (e.g., `.foo`) + // * node type selectors like `span` + // * ` ` descendant selectors + // * `>` child element selectors + // * `#foo` style ID selectors + // * `*` universal selector + // * `~`, the immediately preceeded-by sibling selector + // * `+`, the preceeded-by sibling selector + // * attribute queries: + // | * `[foo]` attribute presence selector + // | * `[foo='bar']` attribute value exact match + // | * `[foo~='bar']` attribute value list item match + // | * `[foo^='bar']` attribute start match + // | * `[foo$='bar']` attribute end match + // | * `[foo*='bar']` attribute substring match + // * `:first-child`, `:last-child`, and `:only-child` positional selectors + // * `:empty` content emtpy selector + // * `:checked` pseudo selector + // * `:nth-child(n)`, `:nth-child(2n+1)` style positional calculations + // * `:nth-child(even)`, `:nth-child(odd)` positional selectors + // * `:not(...)` negation pseudo selectors + // + // Any legal combination of these selectors will work with + // `dojo.query()`, including compound selectors ("," delimited). + // Very complex and useful searches can be constructed with this + // palette of selectors and when combined with functions for + // manipulation presented by dojo.NodeList, many types of DOM + // manipulation operations become very straightforward. + // + // Unsupported Selectors: + // ---------------------- + // + // While dojo.query handles many CSS3 selectors, some fall outside of + // what's resaonable for a programmatic node querying engine to + // handle. Currently unsupported selectors include: + // + // * namespace-differentiated selectors of any form + // * all `::` pseduo-element selectors + // * certain pseduo-selectors which don't get a lot of day-to-day use: + // | * `:root`, `:lang()`, `:target`, `:focus` + // * all visual and state selectors: + // | * `:root`, `:active`, `:hover`, `:visisted`, `:link`, + // `:enabled`, `:disabled` + // * `:*-of-type` pseudo selectors + // + // dojo.query and XML Documents: + // ----------------------------- + // + // `dojo.query` (as of dojo 1.2) supports searching XML documents + // in a case-sensitive manner. If an HTML document is served with + // a doctype that forces case-sensitivity (e.g., XHTML 1.1 + // Strict), dojo.query() will detect this and "do the right + // thing". Case sensitivity is dependent upon the document being + // searched and not the query used. It is therefore possible to + // use case-sensitive queries on strict sub-documents (iframes, + // etc.) or XML documents while still assuming case-insensitivity + // for a host/root document. + // + // Non-selector Queries: + // --------------------- + // + // If something other than a String is passed for the query, + // `dojo.query` will return a new `dojo.NodeList` instance + // constructed from that parameter alone and all further + // processing will stop. This means that if you have a reference + // to a node or NodeList, you can quickly construct a new NodeList + // from the original by calling `dojo.query(node)` or + // `dojo.query(list)`. + // + // query: + // The CSS3 expression to match against. For details on the syntax of + // CSS3 selectors, see <http://www.w3.org/TR/css3-selectors/#selectors> + // root: + // A DOMNode (or node id) to scope the search from. Optional. + // returns: dojo.NodeList + // An instance of `dojo.NodeList`. Many methods are available on + // NodeLists for searching, iterating, manipulating, and handling + // events on the matched nodes in the returned list. + // example: + // search the entire document for elements with the class "foo": + // | dojo.query(".foo"); + // these elements will match: + // | <span class="foo"></span> + // | <span class="foo bar"></span> + // | <p class="thud foo"></p> + // example: + // search the entire document for elements with the classes "foo" *and* "bar": + // | dojo.query(".foo.bar"); + // these elements will match: + // | <span class="foo bar"></span> + // while these will not: + // | <span class="foo"></span> + // | <p class="thud foo"></p> + // example: + // find `<span>` elements which are descendants of paragraphs and + // which have a "highlighted" class: + // | dojo.query("p span.highlighted"); + // the innermost span in this fragment matches: + // | <p class="foo"> + // | <span>... + // | <span class="highlighted foo bar">...</span> + // | </span> + // | </p> + // example: + // set an "odd" class on all odd table rows inside of the table + // `#tabular_data`, using the `>` (direct child) selector to avoid + // affecting any nested tables: + // | dojo.query("#tabular_data > tbody > tr:nth-child(odd)").addClass("odd"); + // example: + // remove all elements with the class "error" from the document + // and store them in a list: + // | var errors = dojo.query(".error").orphan(); + // example: + // add an onclick handler to every submit button in the document + // which causes the form to be sent via Ajax instead: + // | dojo.query("input[type='submit']").onclick(function(e){ + // | dojo.stopEvent(e); // prevent sending the form + // | var btn = e.target; + // | dojo.xhrPost({ + // | form: btn.form, + // | load: function(data){ + // | // replace the form with the response + // | var div = dojo.doc.createElement("div"); + // | dojo.place(div, btn.form, "after"); + // | div.innerHTML = data; + // | dojo.style(btn.form, "display", "none"); + // | } + // | }); + // | }); + + //Set list constructor to desired value. This can change + //between calls, so always re-assign here. + qlc = d._queryListCtor; + + if(!query){ + return new qlc(); + } + + if(query.constructor == qlc){ + return query; + } + if(!isString(query)){ + return new qlc(query); // dojo.NodeList + } + if(isString(root)){ + root = d.byId(root); + if(!root){ return new qlc(); } + } + + root = root||getDoc(); + var od = root.ownerDocument||root.documentElement; + + // throw the big case sensitivity switch + + // NOTE: + // Opera in XHTML mode doesn't detect case-sensitivity correctly + // and it's not clear that there's any way to test for it + caseSensitive = (root.contentType && root.contentType=="application/xml") || + (d.isOpera && (root.doctype || od.toString() == "[object XMLDocument]")) || + (!!od) && + (d.isIE ? od.xml : (root.xmlVersion||od.xmlVersion)); + + // NOTE: + // adding "true" as the 2nd argument to getQueryFunc is useful for + // testing the DOM branch without worrying about the + // behavior/performance of the QSA branch. + var r = getQueryFunc(query)(root); + + // FIXME: + // need to investigate this branch WRT #8074 and #8075 + if(r && r.nozip && !qlc._wrap){ + return r; + } + return _zip(r); // dojo.NodeList + } + + // FIXME: need to add infrastructure for post-filtering pseudos, ala :last + d.query.pseudos = pseudos; + + // one-off function for filtering a NodeList based on a simple selector + d._filterQueryResult = function(nodeList, simpleFilter){ + var tmpNodeList = new d._queryListCtor(); + var filterFunc = getSimpleFilterFunc(getQueryParts(simpleFilter)[0]); + for(var x = 0, te; te = nodeList[x]; x++){ + if(filterFunc(te)){ tmpNodeList.push(te); } + } + return tmpNodeList; + } +})(this["queryPortability"]||this["acme"]||dojo); + +/* +*/ + +} + +if(!dojo._hasResource["dojo._base.xhr"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.xhr"] = true; +dojo.provide("dojo._base.xhr"); + + + + + +(function(){ + var _d = dojo; + function setValue(/*Object*/obj, /*String*/name, /*String*/value){ + //summary: + // For the named property in object, set the value. If a value + // already exists and it is a string, convert the value to be an + // array of values. + var val = obj[name]; + if(_d.isString(val)){ + obj[name] = [val, value]; + }else if(_d.isArray(val)){ + val.push(value); + }else{ + obj[name] = value; + } + } + + dojo.formToObject = function(/*DOMNode||String*/ formNode){ + // summary: + // dojo.formToObject returns the values encoded in an HTML form as + // string properties in an object which it then returns. Disabled form + // elements, buttons, and other non-value form elements are skipped. + // Multi-select elements are returned as an array of string values. + // description: + // This form: + // + // | <form id="test_form"> + // | <input type="text" name="blah" value="blah"> + // | <input type="text" name="no_value" value="blah" disabled> + // | <input type="button" name="no_value2" value="blah"> + // | <select type="select" multiple name="multi" size="5"> + // | <option value="blah">blah</option> + // | <option value="thud" selected>thud</option> + // | <option value="thonk" selected>thonk</option> + // | </select> + // | </form> + // + // yields this object structure as the result of a call to + // formToObject(): + // + // | { + // | blah: "blah", + // | multi: [ + // | "thud", + // | "thonk" + // | ] + // | }; + + var ret = {}; + var exclude = "file|submit|image|reset|button|"; + _d.forEach(dojo.byId(formNode).elements, function(item){ + var _in = item.name; + var type = (item.type||"").toLowerCase(); + if(_in && type && exclude.indexOf(type) == -1 && !item.disabled){ + if(type == "radio" || type == "checkbox"){ + if(item.checked){ setValue(ret, _in, item.value); } + }else if(item.multiple){ + ret[_in] = []; + _d.query("option", item).forEach(function(opt){ + if(opt.selected){ + setValue(ret, _in, opt.value); + } + }); + }else{ + setValue(ret, _in, item.value); + if(type == "image"){ + ret[_in+".x"] = ret[_in+".y"] = ret[_in].x = ret[_in].y = 0; + } + } + } + }); + return ret; // Object + } + + dojo.objectToQuery = function(/*Object*/ map){ + // summary: + // takes a name/value mapping object and returns a string representing + // a URL-encoded version of that object. + // example: + // this object: + // + // | { + // | blah: "blah", + // | multi: [ + // | "thud", + // | "thonk" + // | ] + // | }; + // + // yields the following query string: + // + // | "blah=blah&multi=thud&multi=thonk" + + // FIXME: need to implement encodeAscii!! + var enc = encodeURIComponent; + var pairs = []; + var backstop = {}; + for(var name in map){ + var value = map[name]; + if(value != backstop[name]){ + var assign = enc(name) + "="; + if(_d.isArray(value)){ + for(var i=0; i < value.length; i++){ + pairs.push(assign + enc(value[i])); + } + }else{ + pairs.push(assign + enc(value)); + } + } + } + return pairs.join("&"); // String + } + + dojo.formToQuery = function(/*DOMNode||String*/ formNode){ + // summary: + // Returns a URL-encoded string representing the form passed as either a + // node or string ID identifying the form to serialize + return _d.objectToQuery(_d.formToObject(formNode)); // String + } + + dojo.formToJson = function(/*DOMNode||String*/ formNode, /*Boolean?*/prettyPrint){ + // summary: + // return a serialized JSON string from a form node or string + // ID identifying the form to serialize + return _d.toJson(_d.formToObject(formNode), prettyPrint); // String + } + + dojo.queryToObject = function(/*String*/ str){ + // summary: + // returns an object representing a de-serialized query section of a + // URL. Query keys with multiple values are returned in an array. + // description: + // This string: + // + // | "foo=bar&foo=baz&thinger=%20spaces%20=blah&zonk=blarg&" + // + // results in this object structure: + // + // | { + // | foo: [ "bar", "baz" ], + // | thinger: " spaces =blah", + // | zonk: "blarg" + // | } + // + // Note that spaces and other urlencoded entities are correctly + // handled. + + // FIXME: should we grab the URL string if we're not passed one? + var ret = {}; + var qp = str.split("&"); + var dec = decodeURIComponent; + _d.forEach(qp, function(item){ + if(item.length){ + var parts = item.split("="); + var name = dec(parts.shift()); + var val = dec(parts.join("=")); + if(_d.isString(ret[name])){ + ret[name] = [ret[name]]; + } + if(_d.isArray(ret[name])){ + ret[name].push(val); + }else{ + ret[name] = val; + } + } + }); + return ret; // Object + } + + /* + from refactor.txt: + + all bind() replacement APIs take the following argument structure: + + { + url: "blah.html", + + // all below are optional, but must be supported in some form by + // every IO API + timeout: 1000, // milliseconds + handleAs: "text", // replaces the always-wrong "mimetype" + content: { + key: "value" + }, + + // browser-specific, MAY be unsupported + sync: true, // defaults to false + form: dojo.byId("someForm") + } + */ + + // need to block async callbacks from snatching this thread as the result + // of an async callback might call another sync XHR, this hangs khtml forever + // must checked by watchInFlight() + + dojo._blockAsync = false; + + dojo._contentHandlers = { + text: function(xhr){ return xhr.responseText; }, + json: function(xhr){ + return _d.fromJson(xhr.responseText || null); + }, + "json-comment-filtered": function(xhr){ + // NOTE: the json-comment-filtered option was implemented to prevent + // "JavaScript Hijacking", but it is less secure than standard JSON. Use + // standard JSON instead. JSON prefixing can be used to subvert hijacking. + if(!dojo.config.useCommentedJson){ + console.warn("Consider using the standard mimetype:application/json." + + " json-commenting can introduce security issues. To" + + " decrease the chances of hijacking, use the standard the 'json' handler and" + + " prefix your json with: {}&&\n" + + "Use djConfig.useCommentedJson=true to turn off this message."); + } + + var value = xhr.responseText; + var cStartIdx = value.indexOf("\/*"); + var cEndIdx = value.lastIndexOf("*\/"); + if(cStartIdx == -1 || cEndIdx == -1){ + throw new Error("JSON was not comment filtered"); + } + return _d.fromJson(value.substring(cStartIdx+2, cEndIdx)); + }, + javascript: function(xhr){ + // FIXME: try Moz and IE specific eval variants? + return _d.eval(xhr.responseText); + }, + xml: function(xhr){ + var result = xhr.responseXML; + if(_d.isIE && (!result || !result.documentElement)){ + var ms = function(n){ return "MSXML" + n + ".DOMDocument"; } + var dp = ["Microsoft.XMLDOM", ms(6), ms(4), ms(3), ms(2)]; + _d.some(dp, function(p){ + try{ + var dom = new ActiveXObject(p); + dom.async = false; + dom.loadXML(xhr.responseText); + result = dom; + }catch(e){ return false; } + return true; + }); + } + return result; // DOMDocument + } + }; + + dojo._contentHandlers["json-comment-optional"] = function(xhr){ + var handlers = _d._contentHandlers; + if(xhr.responseText && xhr.responseText.indexOf("\/*") != -1){ + return handlers["json-comment-filtered"](xhr); + }else{ + return handlers["json"](xhr); + } + }; + + /*===== + dojo.__IoArgs = function(){ + // url: String + // URL to server endpoint. + // content: Object? + // Contains properties with string values. These + // properties will be serialized as name1=value2 and + // passed in the request. + // timeout: Integer? + // Milliseconds to wait for the response. If this time + // passes, the then error callbacks are called. + // form: DOMNode? + // DOM node for a form. Used to extract the form values + // and send to the server. + // preventCache: Boolean? + // Default is false. If true, then a + // "dojo.preventCache" parameter is sent in the request + // with a value that changes with each request + // (timestamp). Useful only with GET-type requests. + // handleAs: String? + // Acceptable values depend on the type of IO + // transport (see specific IO calls for more information). + // load: Function? + // function(response, ioArgs){} response is of type Object, ioArgs + // is of type dojo.__IoCallbackArgs. This function will be + // called on a successful HTTP response code. + // error: Function? + // function(response, ioArgs){} response is of type Object, ioArgs + // is of type dojo.__IoCallbackArgs. This function will + // be called when the request fails due to a network or server error, the url + // is invalid, etc. It will also be called if the load or handle callback throws an + // exception, unless djConfig.debugAtAllCosts is true. This allows deployed applications + // to continue to run even when a logic error happens in the callback, while making + // it easier to troubleshoot while in debug mode. + // handle: Function? + // function(response, ioArgs){} response is of type Object, ioArgs + // is of type dojo.__IoCallbackArgs. This function will + // be called at the end of every request, whether or not an error occurs. + this.url = url; + this.content = content; + this.timeout = timeout; + this.form = form; + this.preventCache = preventCache; + this.handleAs = handleAs; + this.load = load; + this.error = error; + this.handle = handle; + } + =====*/ + + /*===== + dojo.__IoCallbackArgs = function(args, xhr, url, query, handleAs, id, canDelete, json){ + // args: Object + // the original object argument to the IO call. + // xhr: XMLHttpRequest + // For XMLHttpRequest calls only, the + // XMLHttpRequest object that was used for the + // request. + // url: String + // The final URL used for the call. Many times it + // will be different than the original args.url + // value. + // query: String + // For non-GET requests, the + // name1=value1&name2=value2 parameters sent up in + // the request. + // handleAs: String + // The final indicator on how the response will be + // handled. + // id: String + // For dojo.io.script calls only, the internal + // script ID used for the request. + // canDelete: Boolean + // For dojo.io.script calls only, indicates + // whether the script tag that represents the + // request can be deleted after callbacks have + // been called. Used internally to know when + // cleanup can happen on JSONP-type requests. + // json: Object + // For dojo.io.script calls only: holds the JSON + // response for JSONP-type requests. Used + // internally to hold on to the JSON responses. + // You should not need to access it directly -- + // the same object should be passed to the success + // callbacks directly. + this.args = args; + this.xhr = xhr; + this.url = url; + this.query = query; + this.handleAs = handleAs; + this.id = id; + this.canDelete = canDelete; + this.json = json; + } + =====*/ + + + + dojo._ioSetArgs = function(/*dojo.__IoArgs*/args, + /*Function*/canceller, + /*Function*/okHandler, + /*Function*/errHandler){ + // summary: + // sets up the Deferred and ioArgs property on the Deferred so it + // can be used in an io call. + // args: + // The args object passed into the public io call. Recognized properties on + // the args object are: + // canceller: + // The canceller function used for the Deferred object. The function + // will receive one argument, the Deferred object that is related to the + // canceller. + // okHandler: + // The first OK callback to be registered with Deferred. It has the opportunity + // to transform the OK response. It will receive one argument -- the Deferred + // object returned from this function. + // errHandler: + // The first error callback to be registered with Deferred. It has the opportunity + // to do cleanup on an error. It will receive two arguments: error (the + // Error object) and dfd, the Deferred object returned from this function. + + var ioArgs = {args: args, url: args.url}; + + //Get values from form if requestd. + var formObject = null; + if(args.form){ + var form = _d.byId(args.form); + //IE requires going through getAttributeNode instead of just getAttribute in some form cases, + //so use it for all. See #2844 + var actnNode = form.getAttributeNode("action"); + ioArgs.url = ioArgs.url || (actnNode ? actnNode.value : null); + formObject = _d.formToObject(form); + } + + // set up the query params + var miArgs = [{}]; + + if(formObject){ + // potentially over-ride url-provided params w/ form values + miArgs.push(formObject); + } + if(args.content){ + // stuff in content over-rides what's set by form + miArgs.push(args.content); + } + if(args.preventCache){ + miArgs.push({"dojo.preventCache": new Date().valueOf()}); + } + ioArgs.query = _d.objectToQuery(_d.mixin.apply(null, miArgs)); + + // .. and the real work of getting the deferred in order, etc. + ioArgs.handleAs = args.handleAs || "text"; + var d = new _d.Deferred(canceller); + d.addCallbacks(okHandler, function(error){ + return errHandler(error, d); + }); + + //Support specifying load, error and handle callback functions from the args. + //For those callbacks, the "this" object will be the args object. + //The callbacks will get the deferred result value as the + //first argument and the ioArgs object as the second argument. + var ld = args.load; + if(ld && _d.isFunction(ld)){ + d.addCallback(function(value){ + return ld.call(args, value, ioArgs); + }); + } + var err = args.error; + if(err && _d.isFunction(err)){ + d.addErrback(function(value){ + return err.call(args, value, ioArgs); + }); + } + var handle = args.handle; + if(handle && _d.isFunction(handle)){ + d.addBoth(function(value){ + return handle.call(args, value, ioArgs); + }); + } + + d.ioArgs = ioArgs; + + // FIXME: need to wire up the xhr object's abort method to something + // analagous in the Deferred + return d; + } + + var _deferredCancel = function(/*Deferred*/dfd){ + //summary: canceller function for dojo._ioSetArgs call. + + dfd.canceled = true; + var xhr = dfd.ioArgs.xhr; + var _at = typeof xhr.abort; + if(_at == "function" || _at == "object" || _at == "unknown"){ + xhr.abort(); + } + var err = dfd.ioArgs.error; + if(!err){ + err = new Error("xhr cancelled"); + err.dojoType="cancel"; + } + return err; + } + var _deferredOk = function(/*Deferred*/dfd){ + //summary: okHandler function for dojo._ioSetArgs call. + + var ret = _d._contentHandlers[dfd.ioArgs.handleAs](dfd.ioArgs.xhr); + return ret === undefined ? null : ret; + } + var _deferError = function(/*Error*/error, /*Deferred*/dfd){ + //summary: errHandler function for dojo._ioSetArgs call. + + console.error(error); + return error; + } + + // avoid setting a timer per request. It degrades performance on IE + // something fierece if we don't use unified loops. + var _inFlightIntvl = null; + var _inFlight = []; + var _watchInFlight = function(){ + //summary: + // internal method that checks each inflight XMLHttpRequest to see + // if it has completed or if the timeout situation applies. + + var now = (new Date()).getTime(); + // make sure sync calls stay thread safe, if this callback is called + // during a sync call and this results in another sync call before the + // first sync call ends the browser hangs + if(!_d._blockAsync){ + // we need manual loop because we often modify _inFlight (and therefore 'i') while iterating + // note: the second clause is an assigment on purpose, lint may complain + for(var i = 0, tif; i < _inFlight.length && (tif = _inFlight[i]); i++){ + var dfd = tif.dfd; + var func = function(){ + if(!dfd || dfd.canceled || !tif.validCheck(dfd)){ + _inFlight.splice(i--, 1); + }else if(tif.ioCheck(dfd)){ + _inFlight.splice(i--, 1); + tif.resHandle(dfd); + }else if(dfd.startTime){ + //did we timeout? + if(dfd.startTime + (dfd.ioArgs.args.timeout || 0) < now){ + _inFlight.splice(i--, 1); + var err = new Error("timeout exceeded"); + err.dojoType = "timeout"; + dfd.errback(err); + //Cancel the request so the io module can do appropriate cleanup. + dfd.cancel(); + } + } + }; + if(dojo.config.debugAtAllCosts){ + func.call(this); + }else{ + try{ + func.call(this); + }catch(e){ + dfd.errback(e); + } + } + } + } + + if(!_inFlight.length){ + clearInterval(_inFlightIntvl); + _inFlightIntvl = null; + return; + } + + } + + dojo._ioCancelAll = function(){ + //summary: Cancels all pending IO requests, regardless of IO type + //(xhr, script, iframe). + try{ + _d.forEach(_inFlight, function(i){ + try{ + i.dfd.cancel(); + }catch(e){/*squelch*/} + }); + }catch(e){/*squelch*/} + } + + //Automatically call cancel all io calls on unload + //in IE for trac issue #2357. + if(_d.isIE){ + _d.addOnWindowUnload(_d._ioCancelAll); + } + + _d._ioWatch = function(/*Deferred*/dfd, + /*Function*/validCheck, + /*Function*/ioCheck, + /*Function*/resHandle){ + //summary: watches the io request represented by dfd to see if it completes. + //dfd: + // The Deferred object to watch. + //validCheck: + // Function used to check if the IO request is still valid. Gets the dfd + // object as its only argument. + //ioCheck: + // Function used to check if basic IO call worked. Gets the dfd + // object as its only argument. + //resHandle: + // Function used to process response. Gets the dfd + // object as its only argument. + var args = dfd.ioArgs.args; + if(args.timeout){ + dfd.startTime = (new Date()).getTime(); + } + _inFlight.push({dfd: dfd, validCheck: validCheck, ioCheck: ioCheck, resHandle: resHandle}); + if(!_inFlightIntvl){ + _inFlightIntvl = setInterval(_watchInFlight, 50); + } + // handle sync requests + //A weakness: async calls in flight + //could have their handlers called as part of the + //_watchInFlight call, before the sync's callbacks + // are called. + if(args.sync){ + _watchInFlight(); + } + } + + var _defaultContentType = "application/x-www-form-urlencoded"; + + var _validCheck = function(/*Deferred*/dfd){ + return dfd.ioArgs.xhr.readyState; //boolean + } + var _ioCheck = function(/*Deferred*/dfd){ + return 4 == dfd.ioArgs.xhr.readyState; //boolean + } + var _resHandle = function(/*Deferred*/dfd){ + var xhr = dfd.ioArgs.xhr; + if(_d._isDocumentOk(xhr)){ + dfd.callback(dfd); + }else{ + var err = new Error("Unable to load " + dfd.ioArgs.url + " status:" + xhr.status); + err.status = xhr.status; + err.responseText = xhr.responseText; + dfd.errback(err); + } + } + + dojo._ioAddQueryToUrl = function(/*dojo.__IoCallbackArgs*/ioArgs){ + //summary: Adds query params discovered by the io deferred construction to the URL. + //Only use this for operations which are fundamentally GET-type operations. + if(ioArgs.query.length){ + ioArgs.url += (ioArgs.url.indexOf("?") == -1 ? "?" : "&") + ioArgs.query; + ioArgs.query = null; + } + } + + /*===== + dojo.declare("dojo.__XhrArgs", dojo.__IoArgs, { + constructor: function(){ + // summary: + // In addition to the properties listed for the dojo._IoArgs type, + // the following properties are allowed for dojo.xhr* methods. + // handleAs: String? + // Acceptable values are: text (default), json, json-comment-optional, + // json-comment-filtered, javascript, xml + // sync: Boolean? + // false is default. Indicates whether the request should + // be a synchronous (blocking) request. + // headers: Object? + // Additional HTTP headers to send in the request. + this.handleAs = handleAs; + this.sync = sync; + this.headers = headers; + } + }); + =====*/ + + dojo.xhr = function(/*String*/ method, /*dojo.__XhrArgs*/ args, /*Boolean?*/ hasBody){ + // summary: + // Sends an HTTP request with the given method. + // description: + // Sends an HTTP request with the given method. + // See also dojo.xhrGet(), xhrPost(), xhrPut() and dojo.xhrDelete() for shortcuts + // for those HTTP methods. There are also methods for "raw" PUT and POST methods + // via dojo.rawXhrPut() and dojo.rawXhrPost() respectively. + // method: + // HTTP method to be used, such as GET, POST, PUT, DELETE. Should be uppercase. + // hasBody: + // If the request has an HTTP body, then pass true for hasBody. + + //Make the Deferred object for this xhr request. + var dfd = _d._ioSetArgs(args, _deferredCancel, _deferredOk, _deferError); + + //Pass the args to _xhrObj, to allow xhr iframe proxy interceptions. + dfd.ioArgs.xhr = _d._xhrObj(dfd.ioArgs.args); + + if(hasBody){ + if("postData" in args){ + dfd.ioArgs.query = args.postData; + }else if("putData" in args){ + dfd.ioArgs.query = args.putData; + } + }else{ + _d._ioAddQueryToUrl(dfd.ioArgs); + } + + // IE 6 is a steaming pile. It won't let you call apply() on the native function (xhr.open). + // workaround for IE6's apply() "issues" + var ioArgs = dfd.ioArgs; + var xhr = ioArgs.xhr; + xhr.open(method, ioArgs.url, args.sync !== true, args.user || undefined, args.password || undefined); + if(args.headers){ + for(var hdr in args.headers){ + if(hdr.toLowerCase() === "content-type" && !args.contentType){ + args.contentType = args.headers[hdr]; + }else{ + xhr.setRequestHeader(hdr, args.headers[hdr]); + } + } + } + // FIXME: is this appropriate for all content types? + xhr.setRequestHeader("Content-Type", args.contentType || _defaultContentType); + if(!args.headers || !args.headers["X-Requested-With"]){ + xhr.setRequestHeader("X-Requested-With", "XMLHttpRequest"); + } + // FIXME: set other headers here! + if(dojo.config.debugAtAllCosts){ + xhr.send(ioArgs.query); + }else{ + try{ + xhr.send(ioArgs.query); + }catch(e){ + dfd.ioArgs.error = e; + dfd.cancel(); + } + } + _d._ioWatch(dfd, _validCheck, _ioCheck, _resHandle); + xhr = null; + return dfd; // dojo.Deferred + } + + dojo.xhrGet = function(/*dojo.__XhrArgs*/ args){ + // summary: + // Sends an HTTP GET request to the server. + return _d.xhr("GET", args); // dojo.Deferred + } + + dojo.rawXhrPost = dojo.xhrPost = function(/*dojo.__XhrArgs*/ args){ + // summary: + // Sends an HTTP POST request to the server. In addtion to the properties + // listed for the dojo.__XhrArgs type, the following property is allowed: + // postData: + // String. Send raw data in the body of the POST request. + return _d.xhr("POST", args, true); // dojo.Deferred + } + + dojo.rawXhrPut = dojo.xhrPut = function(/*dojo.__XhrArgs*/ args){ + // summary: + // Sends an HTTP PUT request to the server. In addtion to the properties + // listed for the dojo.__XhrArgs type, the following property is allowed: + // putData: + // String. Send raw data in the body of the PUT request. + return _d.xhr("PUT", args, true); // dojo.Deferred + } + + dojo.xhrDelete = function(/*dojo.__XhrArgs*/ args){ + // summary: + // Sends an HTTP DELETE request to the server. + return _d.xhr("DELETE", args); //dojo.Deferred + } + + /* + dojo.wrapForm = function(formNode){ + //summary: + // A replacement for FormBind, but not implemented yet. + + // FIXME: need to think harder about what extensions to this we might + // want. What should we allow folks to do w/ this? What events to + // set/send? + throw new Error("dojo.wrapForm not yet implemented"); + } + */ +})(); + +} + +if(!dojo._hasResource["dojo._base.fx"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.fx"] = true; +dojo.provide("dojo._base.fx"); + + + + + + +/* + Animation losely package based on Dan Pupius' work, contributed under CLA: + http://pupius.co.uk/js/Toolkit.Drawing.js +*/ +(function(){ + + var d = dojo; + var _mixin = d.mixin; + + dojo._Line = function(/*int*/ start, /*int*/ end){ + // summary: + // dojo._Line is the object used to generate values from a start value + // to an end value + // start: int + // Beginning value for range + // end: int + // Ending value for range + this.start = start; + this.end = end; + } + dojo._Line.prototype.getValue = function(/*float*/ n){ + // summary: Returns the point on the line + // n: a floating point number greater than 0 and less than 1 + return ((this.end - this.start) * n) + this.start; // Decimal + } + + d.declare("dojo._Animation", null, { + // summary + // A generic animation class that fires callbacks into its handlers + // object at various states. Nearly all dojo animation functions + // return an instance of this method, usually without calling the + // .play() method beforehand. Therefore, you will likely need to + // call .play() on instances of dojo._Animation when one is + // returned. + constructor: function(/*Object*/ args){ + _mixin(this, args); + if(d.isArray(this.curve)){ + /* curve: Array + pId: a */ + this.curve = new d._Line(this.curve[0], this.curve[1]); + } + }, + + // duration: Integer + // The time in milliseonds the animation will take to run + duration: 350, + + /*===== + // curve: dojo._Line||Array + // A two element array of start and end values, or a dojo._Line instance to be + // used in the Animation. + curve: null, + + // easing: Function + // A Function to adjust the acceleration (or deceleration) of the progress + // across a dojo._Line + easing: null, + =====*/ + + // repeat: Integer + // The number of times to loop the animation + repeat: 0, + + // rate: Integer + // the time in milliseconds to wait before advancing to next frame + // (used as a fps timer: rate/1000 = fps) + rate: 10 /* 100 fps */, + + /*===== + // delay: Integer + // The time in milliseconds to wait before starting animation after it has been .play()'ed + delay: null, + + // events + // + // beforeBegin: Event + // Synthetic event fired before a dojo._Animation begins playing (synchronous) + beforeBegin: null, + + // onBegin: Event + // Synthetic event fired as a dojo._Animation begins playing (useful?) + onBegin: null, + + // onAnimate: Event + // Synthetic event fired at each interval of a dojo._Animation + onAnimate: null, + + // onEnd: Event + // Synthetic event fired after the final frame of a dojo._Animation + onEnd: null, + + // onPlay: Event + // Synthetic event fired any time a dojo._Animation is play()'ed + onPlay: null, + + // onPause: Event + // Synthetic event fired when a dojo._Animation is paused + onPause: null, + + // onStop: Event + // Synthetic event fires when a dojo._Animation is stopped + onStop: null, + + =====*/ + + _percent: 0, + _startRepeatCount: 0, + + _fire: function(/*Event*/ evt, /*Array?*/ args){ + // summary: + // Convenience function. Fire event "evt" and pass it the + // arguments specified in "args". + // evt: + // The event to fire. + // args: + // The arguments to pass to the event. + if(this[evt]){ + if(dojo.config.debugAtAllCosts){ + this[evt].apply(this, args||[]); + }else{ + try{ + this[evt].apply(this, args||[]); + }catch(e){ + // squelch and log because we shouldn't allow exceptions in + // synthetic event handlers to cause the internal timer to run + // amuck, potentially pegging the CPU. I'm not a fan of this + // squelch, but hopefully logging will make it clear what's + // going on + console.error("exception in animation handler for:", evt); + console.error(e); + } + } + } + return this; // dojo._Animation + }, + + play: function(/*int?*/ delay, /*Boolean?*/ gotoStart){ + // summary: + // Start the animation. + // delay: + // How many milliseconds to delay before starting. + // gotoStart: + // If true, starts the animation from the beginning; otherwise, + // starts it from its current position. + var _t = this; + if(_t._delayTimer){ _t._clearTimer(); } + if(gotoStart){ + _t._stopTimer(); + _t._active = _t._paused = false; + _t._percent = 0; + }else if(_t._active && !_t._paused){ + return _t; // dojo._Animation + } + + _t._fire("beforeBegin"); + + var de = delay || _t.delay, + _p = dojo.hitch(_t, "_play", gotoStart); + + if(de > 0){ + _t._delayTimer = setTimeout(_p, de); + return _t; // dojo._Animation + } + _p(); + return _t; + }, + + _play: function(gotoStart){ + var _t = this; + if(_t._delayTimer){ _t._clearTimer(); } + _t._startTime = new Date().valueOf(); + if(_t._paused){ + _t._startTime -= _t.duration * _t._percent; + } + _t._endTime = _t._startTime + _t.duration; + + _t._active = true; + _t._paused = false; + + var value = _t.curve.getValue(_t._percent); + if(!_t._percent){ + if(!_t._startRepeatCount){ + _t._startRepeatCount = _t.repeat; + } + _t._fire("onBegin", [value]); + } + + _t._fire("onPlay", [value]); + + _t._cycle(); + return _t; // dojo._Animation + }, + + pause: function(){ + // summary: Pauses a running animation. + var _t = this; + if(_t._delayTimer){ _t._clearTimer(); } + _t._stopTimer(); + if(!_t._active){ return _t; /*dojo._Animation*/ } + _t._paused = true; + _t._fire("onPause", [_t.curve.getValue(_t._percent)]); + return _t; // dojo._Animation + }, + + gotoPercent: function(/*Decimal*/ percent, /*Boolean?*/ andPlay){ + // summary: + // Sets the progress of the animation. + // percent: + // A percentage in decimal notation (between and including 0.0 and 1.0). + // andPlay: + // If true, play the animation after setting the progress. + var _t = this; + _t._stopTimer(); + _t._active = _t._paused = true; + _t._percent = percent; + if(andPlay){ _t.play(); } + return _t; // dojo._Animation + }, + + stop: function(/*boolean?*/ gotoEnd){ + // summary: Stops a running animation. + // gotoEnd: If true, the animation will end. + var _t = this; + if(_t._delayTimer){ _t._clearTimer(); } + if(!_t._timer){ return _t; /* dojo._Animation */ } + _t._stopTimer(); + if(gotoEnd){ + _t._percent = 1; + } + _t._fire("onStop", [_t.curve.getValue(_t._percent)]); + _t._active = _t._paused = false; + return _t; // dojo._Animation + }, + + status: function(){ + // summary: Returns a string token representation of the status of + // the animation, one of: "paused", "playing", "stopped" + if(this._active){ + return this._paused ? "paused" : "playing"; // String + } + return "stopped"; // String + }, + + _cycle: function(){ + var _t = this; + if(_t._active){ + var curr = new Date().valueOf(); + var step = (curr - _t._startTime) / (_t._endTime - _t._startTime); + + if(step >= 1){ + step = 1; + } + _t._percent = step; + + // Perform easing + if(_t.easing){ + step = _t.easing(step); + } + + _t._fire("onAnimate", [_t.curve.getValue(step)]); + + if(_t._percent < 1){ + _t._startTimer(); + }else{ + _t._active = false; + + if(_t.repeat > 0){ + _t.repeat--; + _t.play(null, true); + }else if(_t.repeat == -1){ + _t.play(null, true); + }else{ + if(_t._startRepeatCount){ + _t.repeat = _t._startRepeatCount; + _t._startRepeatCount = 0; + } + } + _t._percent = 0; + _t._fire("onEnd"); + _t._stopTimer(); + } + } + return _t; // dojo._Animation + }, + + _clearTimer: function(){ + // summary: Clear the play delay timer + clearTimeout(this._delayTimer); + delete this._delayTimer; + } + + }); + + var ctr = 0, + _globalTimerList = [], + timer = null, + runner = { + run: function(){ } + }; + + dojo._Animation.prototype._startTimer = function(){ + // this._timer = setTimeout(dojo.hitch(this, "_cycle"), this.rate); + if(!this._timer){ + this._timer = d.connect(runner, "run", this, "_cycle"); + ctr++; + } + if(!timer){ + timer = setInterval(d.hitch(runner, "run"), this.rate); + } + }; + + dojo._Animation.prototype._stopTimer = function(){ + if(this._timer){ + d.disconnect(this._timer); + this._timer = null; + ctr--; + } + if(ctr <= 0){ + clearInterval(timer); + timer = null; + ctr = 0; + } + }; + + var _makeFadeable = + d.isIE ? function(node){ + // only set the zoom if the "tickle" value would be the same as the + // default + var ns = node.style; + // don't set the width to auto if it didn't already cascade that way. + // We don't want to f anyones designs + if(!ns.width.length && d.style(node, "width") == "auto"){ + ns.width = "auto"; + } + } : + function(){}; + + dojo._fade = function(/*Object*/ args){ + // summary: + // Returns an animation that will fade the node defined by + // args.node from the start to end values passed (args.start + // args.end) (end is mandatory, start is optional) + + args.node = d.byId(args.node); + var fArgs = _mixin({ properties: {} }, args), + props = (fArgs.properties.opacity = {}); + + props.start = !("start" in fArgs) ? + function(){ + return +d.style(fArgs.node, "opacity")||0; + } : fArgs.start; + props.end = fArgs.end; + + var anim = d.animateProperty(fArgs); + d.connect(anim, "beforeBegin", d.partial(_makeFadeable, fArgs.node)); + + return anim; // dojo._Animation + } + + /*===== + dojo.__FadeArgs = function(node, duration, easing){ + // node: DOMNode|String + // The node referenced in the animation + // duration: Integer? + // Duration of the animation in milliseconds. + // easing: Function? + // An easing function. + this.node = node; + this.duration = duration; + this.easing = easing; + } + =====*/ + + dojo.fadeIn = function(/*dojo.__FadeArgs*/ args){ + // summary: + // Returns an animation that will fade node defined in 'args' from + // its current opacity to fully opaque. + return d._fade(_mixin({ end: 1 }, args)); // dojo._Animation + } + + dojo.fadeOut = function(/*dojo.__FadeArgs*/ args){ + // summary: + // Returns an animation that will fade node defined in 'args' + // from its current opacity to fully transparent. + return d._fade(_mixin({ end: 0 }, args)); // dojo._Animation + } + + dojo._defaultEasing = function(/*Decimal?*/ n){ + // summary: The default easing function for dojo._Animation(s) + return 0.5 + ((Math.sin((n + 1.5) * Math.PI))/2); + } + + var PropLine = function(properties){ + // PropLine is an internal class which is used to model the values of + // an a group of CSS properties across an animation lifecycle. In + // particular, the "getValue" function handles getting interpolated + // values between start and end for a particular CSS value. + this._properties = properties; + for(var p in properties){ + var prop = properties[p]; + if(prop.start instanceof d.Color){ + // create a reusable temp color object to keep intermediate results + prop.tempColor = new d.Color(); + } + } + } + + PropLine.prototype.getValue = function(r){ + var ret = {}; + for(var p in this._properties){ + var prop = this._properties[p], + start = prop.start; + if(start instanceof d.Color){ + ret[p] = d.blendColors(start, prop.end, r, prop.tempColor).toCss(); + }else if(!d.isArray(start)){ + ret[p] = ((prop.end - start) * r) + start + (p != "opacity" ? prop.units || "px" : 0); + } + } + return ret; + } + + /*===== + dojo.declare("dojo.__AnimArgs", [dojo.__FadeArgs], { + // Properties: Object? + // A hash map of style properties to Objects describing the transition, + // such as the properties of dojo._Line with an additional 'unit' property + properties: {} + + //TODOC: add event callbacks + }); + =====*/ + + dojo.animateProperty = function(/*dojo.__AnimArgs*/ args){ + // summary: + // Returns an animation that will transition the properties of + // node defined in 'args' depending how they are defined in + // 'args.properties' + // + // description: + // dojo.animateProperty is the foundation of most dojo.fx + // animations. It takes an object of "properties" corresponding to + // style properties, and animates them in parallel over a set + // duration. + // + // example: + // A simple animation that changes the width of the specified node. + // | dojo.animateProperty({ + // | node: "nodeId", + // | properties: { width: 400 }, + // | }).play(); + // Dojo figures out the start value for the width and converts the + // integer specified for the width to the more expressive but + // verbose form `{ width: { end: '400', units: 'px' } }` which you + // can also specify directly + // + // example: + // Animate width, height, and padding over 2 seconds... the + // pedantic way: + // | dojo.animateProperty({ node: node, duration:2000, + // | properties: { + // | width: { start: '200', end: '400', unit:"px" }, + // | height: { start:'200', end: '400', unit:"px" }, + // | paddingTop: { start:'5', end:'50', unit:"px" } + // | } + // | }).play(); + // Note 'paddingTop' is used over 'padding-top'. Multi-name CSS properties + // are written using "mixed case", as the hyphen is illegal as an object key. + // + // example: + // Plug in a different easing function and register a callback for + // when the animation ends. Easing functions accept values between + // zero and one and return a value on that basis. In this case, an + // exponential-in curve. + // | dojo.animateProperty({ + // | node: "nodeId", + // | // dojo figures out the start value + // | properties: { width: { end: 400 } }, + // | easing: function(n){ + // | return (n==0) ? 0 : Math.pow(2, 10 * (n - 1)); + // | }, + // | onEnd: function(){ + // | // called when the animation finishes + // | } + // | }).play(500); // delay playing half a second + // + // example: + // Like all `dojo._Animation`s, animateProperty returns a handle to the + // Animation instance, which fires the events common to Dojo FX. Use `dojo.connect` + // to access these events outside of the Animation definiton: + // | var anim = dojo.animateProperty({ + // | node:"someId", + // | properties:{ + // | width:400, height:500 + // | } + // | }); + // | dojo.connect(anim,"onEnd", function(){ + // | + // | }); + // | // play the animation now: + // | anim.play(); + + args.node = d.byId(args.node); + if(!args.easing){ args.easing = d._defaultEasing; } + + var anim = new d._Animation(args); + d.connect(anim, "beforeBegin", anim, function(){ + var pm = {}; + for(var p in this.properties){ + // Make shallow copy of properties into pm because we overwrite + // some values below. In particular if start/end are functions + // we don't want to overwrite them or the functions won't be + // called if the animation is reused. + if(p == "width" || p == "height"){ + this.node.display = "block"; + } + var prop = this.properties[p]; + prop = pm[p] = _mixin({}, (d.isObject(prop) ? prop: { end: prop })); + + if(d.isFunction(prop.start)){ + prop.start = prop.start(); + } + if(d.isFunction(prop.end)){ + prop.end = prop.end(); + } + var isColor = (p.toLowerCase().indexOf("color") >= 0); + function getStyle(node, p){ + // dojo.style(node, "height") can return "auto" or "" on IE; this is more reliable: + var v = {height: node.offsetHeight, width: node.offsetWidth}[p]; + if(v !== undefined){ return v; } + v = d.style(node, p); + return (p == "opacity") ? +v : (isColor ? v : parseFloat(v)); + } + if(!("end" in prop)){ + prop.end = getStyle(this.node, p); + }else if(!("start" in prop)){ + prop.start = getStyle(this.node, p); + } + + if(isColor){ + prop.start = new d.Color(prop.start); + prop.end = new d.Color(prop.end); + }else{ + prop.start = (p == "opacity") ? +prop.start : parseFloat(prop.start); + } + } + this.curve = new PropLine(pm); + }); + d.connect(anim, "onAnimate", d.hitch(d, "style", anim.node)); + return anim; // dojo._Animation + } + + dojo.anim = function( /*DOMNode|String*/ node, + /*Object*/ properties, + /*Integer?*/ duration, + /*Function?*/ easing, + /*Function?*/ onEnd, + /*Integer?*/ delay){ + // summary: + // A simpler interface to `dojo.animateProperty()`, also returns + // an instance of `dojo._Animation` but begins the animation + // immediately, unlike nearly every other Dojo animation API. + // description: + // `dojo.anim` is a simpler (but somewhat less powerful) version + // of `dojo.animateProperty`. It uses defaults for many basic properties + // and allows for positional parameters to be used in place of the + // packed "property bag" which is used for other Dojo animation + // methods. + // + // The `dojo._Animation` object returned from `dojo.anim` will be + // already playing when it is returned from this function, so + // calling play() on it again is (usually) a no-op. + // node: + // a DOM node or the id of a node to animate CSS properties on + // duration: + // The number of milliseconds over which the animation + // should run. Defaults to the global animation default duration + // (350ms). + // easing: + // An easing function over which to calculate acceleration + // and deceleration of the animation through its duration. + // A default easing algorithm is provided, but you may + // plug in any you wish. A large selection of easing algorithms + // are available in `dojo.fx.easing`. + // onEnd: + // A function to be called when the animation finishes + // running. + // delay: + // The number of milliseconds to delay beginning the + // animation by. The default is 0. + // example: + // Fade out a node + // | dojo.anim("id", { opacity: 0 }); + // example: + // Fade out a node over a full second + // | dojo.anim("id", { opacity: 0 }, 1000); + return d.animateProperty({ + node: node, + duration: duration||d._Animation.prototype.duration, + properties: properties, + easing: easing, + onEnd: onEnd + }).play(delay||0); + } +})(); + +} + +if(!dojo._hasResource["dojo._base.browser"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojo._base.browser"] = true; +dojo.provide("dojo._base.browser"); + + + + + + + + + + +//Need this to be the last code segment in base, so do not place any +//dojo.requireIf calls in this file. Otherwise, due to how the build system +//puts all requireIf dependencies after the current file, the require calls +//could be called before all of base is defined. +dojo.forEach(dojo.config.require, function(i){ + dojo["require"](i); +}); + +} + + //INSERT dojo.i18n._preloadLocalizations HERE + + if(dojo.config.afterOnLoad && dojo.isBrowser){ + //Dojo is being added to the page after page load, so just trigger + //the init sequence after a timeout. Using a timeout so the rest of this + //script gets evaluated properly. This work needs to happen after the + //dojo.config.require work done in dojo._base. + window.setTimeout(dojo._loadInit, 1000); + } + +})(); + Property changes on: branches/vhffs-design/vhffs-panel/js/dojo/dojo.js.uncompressed.js ___________________________________________________________________ Name: svn:mergeinfo + Added: branches/vhffs-design/vhffs-panel/js/dojo/i18n.js =================================================================== --- branches/vhffs-design/vhffs-panel/js/dojo/i18n.js (rev 0) +++ branches/vhffs-design/vhffs-panel/js/dojo/i18n.js 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,171 @@ +/* + Copyright (c) 2004-2009, The Dojo Foundation All Rights Reserved. + Available via Academic Free License >= 2.1 OR the modified BSD license. + see: http://dojotoolkit.org/license for details +*/ + + +if(!dojo._hasResource["dojo.i18n"]){ +dojo._hasResource["dojo.i18n"]=true; +dojo.provide("dojo.i18n"); +dojo.i18n.getLocalization=function(_1,_2,_3){ +_3=dojo.i18n.normalizeLocale(_3); +var _4=_3.split("-"); +var _5=[_1,"nls",_2].join("."); +var _6=dojo._loadedModules[_5]; +if(_6){ +var _7; +for(var i=_4.length;i>0;i--){ +var _9=_4.slice(0,i).join("_"); +if(_6[_9]){ +_7=_6[_9]; +break; +} +} +if(!_7){ +_7=_6.ROOT; +} +if(_7){ +var _a=function(){ +}; +_a.prototype=_7; +return new _a(); +} +} +throw new Error("Bundle not found: "+_2+" in "+_1+" , locale="+_3); +}; +dojo.i18n.normalizeLocale=function(_b){ +var _c=_b?_b.toLowerCase():dojo.locale; +if(_c=="root"){ +_c="ROOT"; +} +return _c; +}; +dojo.i18n._requireLocalization=function(_d,_e,_f,_10){ +var _11=dojo.i18n.normalizeLocale(_f); +var _12=[_d,"nls",_e].join("."); +var _13=""; +if(_10){ +var _14=_10.split(","); +for(var i=0;i<_14.length;i++){ +if(_11["indexOf"](_14[i])==0){ +if(_14[i].length>_13.length){ +_13=_14[i]; +} +} +} +if(!_13){ +_13="ROOT"; +} +} +var _16=_10?_13:_11; +var _17=dojo._loadedModules[_12]; +var _18=null; +if(_17){ +if(dojo.config.localizationComplete&&_17._built){ +return; +} +var _19=_16.replace(/-/g,"_"); +var _1a=_12+"."+_19; +_18=dojo._loadedModules[_1a]; +} +if(!_18){ +_17=dojo["provide"](_12); +var _1b=dojo._getModuleSymbols(_d); +var _1c=_1b.concat("nls").join("/"); +var _1d; +dojo.i18n._searchLocalePath(_16,_10,function(loc){ +var _1f=loc.replace(/-/g,"_"); +var _20=_12+"."+_1f; +var _21=false; +if(!dojo._loadedModules[_20]){ +dojo["provide"](_20); +var _22=[_1c]; +if(loc!="ROOT"){ +_22.push(loc); +} +_22.push(_e); +var _23=_22.join("/")+".js"; +_21=dojo._loadPath(_23,null,function(_24){ +var _25=function(){ +}; +_25.prototype=_1d; +_17[_1f]=new _25(); +for(var j in _24){ +_17[_1f][j]=_24[j]; +} +}); +}else{ +_21=true; +} +if(_21&&_17[_1f]){ +_1d=_17[_1f]; +}else{ +_17[_1f]=_1d; +} +if(_10){ +return true; +} +}); +} +if(_10&&_11!=_13){ +_17[_11.replace(/-/g,"_")]=_17[_13.replace(/-/g,"_")]; +} +}; +(function(){ +var _27=dojo.config.extraLocale; +if(_27){ +if(!_27 instanceof Array){ +_27=[_27]; +} +var req=dojo.i18n._requireLocalization; +dojo.i18n._requireLocalization=function(m,b,_2b,_2c){ +req(m,b,_2b,_2c); +if(_2b){ +return; +} +for(var i=0;i<_27.length;i++){ +req(m,b,_27[i],_2c); +} +}; +} +})(); +dojo.i18n._searchLocalePath=function(_2e,_2f,_30){ +_2e=dojo.i18n.normalizeLocale(_2e); +var _31=_2e.split("-"); +var _32=[]; +for(var i=_31.length;i>0;i--){ +_32.push(_31.slice(0,i).join("-")); +} +_32.push(false); +if(_2f){ +_32.reverse(); +} +for(var j=_32.length-1;j>=0;j--){ +var loc=_32[j]||"ROOT"; +var _36=_30(loc); +if(_36){ +break; +} +} +}; +dojo.i18n._preloadLocalizations=function(_37,_38){ +function _39(_3a){ +_3a=dojo.i18n.normalizeLocale(_3a); +dojo.i18n._searchLocalePath(_3a,true,function(loc){ +for(var i=0;i<_38.length;i++){ +if(_38[i]==loc){ +dojo["require"](_37+"_"+loc); +return true; +} +} +return false; +}); +}; +_39(); +var _3d=dojo.config.extraLocale||[]; +for(var i=0;i<_3d.length;i++){ +_39(_3d[i]); +} +}; +} Modified: branches/vhffs-design/vhffs-panel/lost.pl =================================================================== --- branches/vhffs-design/vhffs-panel/lost.pl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/lost.pl 2009-05-23 13:44:53 UTC (rev 1402) @@ -30,33 +30,58 @@ # POSSIBILITY OF SUCH DAMAGE. -require 5.004; +use strict; use utf8; -use POSIX; -use strict; +use POSIX qw(locale_h); use locale; use Locale::gettext; -use HTML::Template; -use CGI; +use Encode; use lib '%VHFFS_LIB_DIR%'; -use Vhffs::Panel::Main; +use Vhffs::Panel::Anonymous; -my $panel = new Vhffs::Panel::Main(); +my $panel = new Vhffs::Panel::Anonymous(); exit 0 unless $panel; -my $vhffs = $panel->{'vhffs'}; -my $templatedir = $panel->{'templatedir'}; -my $cgi = $panel->{'cgi'}; +my $cgi = $panel->cgi; +my $vhffs = $panel->vhffs; -my $template = new HTML::Template( filename => $templatedir.'/panel/main/lost.tmpl', associate => $cgi ); +my $username = $cgi->param( 'username' ); -#$template->param( TITLE => gettext('VHFFS Password Lost') ); -$template->param( TEXT_LOSTPASS => gettext('You lost your password? You\'re a bad guy!') ); -$template->param( TEXT_BLABLA => gettext('But fortunately we\'re smart, so just type your login here<br/>and a new password will be sent to you by email!') ); -$template->param( TEXT_USERNAME => gettext('Username') ); -$template->param( TEXT_BUTTON => gettext('Give me a new password') ); -$template->param( TEXT_BACK => gettext('Back to login page') ); +if(defined $username) { + # Form has been submitted, let's check + use Vhffs::User; + + my $user = Vhffs::User::get_by_username( $vhffs, $username ); + + if( defined $user && $user->{state} == Vhffs::Constants::ACTIVATED ) { + # TODO Send a confirmation email to avoir abusive + # password reset. + my $password = Vhffs::Functions::generate_random_password; + $user->set_password( $password ); + $user->commit; + + # Change user's box password if any. + my $mu = init Vhffs::Services::MailUser( $vhffs , $user ); + if( defined $mu && $mu->exists_box) { + $mu->changepassword( $password ); + } + + # Send a mail with plain password inside + my $subject = sprintf( gettext('Password changed on %s'), $vhffs->get_config->get_host_name ); + my $content = sprintf(gettext("Hello %s %s,\n\nYou asked for a new password, here are your new login information:\nUser: %s\nPassword: %s\n\n%s Administrators\n"), $user->get_firstname, $user->get_lastname, $user->get_username, $password , $vhffs->get_config->get_host_name ); + $user->send_mail_user( $subject, $content ); + + $panel->add_info( gettext('Password successfully reset') ); + require 'auth.pl'; + exit 0; + } else { + # User not found + $panel->add_error( sprintf( + gettext("User %s was not found. Check the username. If you just created the user, wait, you'll receive a password"), + $username) ); + } +} -$panel->light( $template ); -$panel->display; + +$panel->render('content/anonymous/lost-password.tt', {}); Deleted: branches/vhffs-design/vhffs-panel/lost_ack.pl =================================================================== --- branches/vhffs-design/vhffs-panel/lost_ack.pl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/lost_ack.pl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,91 +0,0 @@ -#!%PERL% -w -# Copyright (c) vhffs project and its contributors -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions -# are met: -# -# 1. Redistributions of source code must retain the above copyright -# notice, this list of conditions and the following disclaimer. -#2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in -# the documentation and/or other materials provided with the -# distribution. -#3. Neither the name of vhffs nor the names of its contributors -# may be used to endorse or promote products derived from this -# software without specific prior written permission. -# -#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -#"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -#LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS -#FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE -#COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, -#INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, -#BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER -#CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN -# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -# POSSIBILITY OF SUCH DAMAGE. - - -use utf8; -use POSIX qw(locale_h); -use HTML::Template; -use locale; -use Locale::gettext; -use CGI; -use CGI::Session; -use strict; - -use lib '%VHFFS_LIB_DIR%'; -use Vhffs::User; -use Vhffs::Main; -use Vhffs::Panel::Main; -use Vhffs::Services::MailUser; -use Vhffs::Functions; - -my $panel = new Vhffs::Panel::Main(); -exit 0 unless $panel; - -my $vhffs = $panel->{'vhffs'}; -my $templatedir = $panel->{'templatedir'}; -my $cgi = $panel->{'cgi'}; -my $username = $cgi->param('username'); -my $user = Vhffs::User::get_by_username( $vhffs, $username ); -my $template; - -if ( defined $user && $user->{'state'} == Vhffs::Constants::ACTIVATED ) -{ - #create a new password for this user - my $password = Vhffs::Functions::generate_random_password; - $user->set_password( $password ); - $user->commit; - my $mu = init Vhffs::Services::MailUser( $vhffs , $user ); - if( defined $mu && $mu->exists_box) { - $mu->changepassword( $password ); - } - - # Send a mail with plain password inside - my $subject = sprintf("Password changed on %s", $vhffs->get_config->get_host_name ); - my $content = sprintf("Hello %s %s,\n\nYou asked for a new password, here are your new login information:\nUser: %s\nPassword: %s\n\n%s Administrators\n", $user->get_firstname, $user->get_lastname, $user->get_username, $password , $vhffs->get_config->get_host_name ); - $user->send_mail_user( $subject, $content ); - - $template = new HTML::Template( filename => $templatedir."/panel/main/lost_ok.tmpl" ); - - $template->param( TEXT_WAITPASS => sprintf( gettext("Please wait %s, a new password will be sent to you in a few minutes..."), $username ) ); - $template->param( TEXT_LOGIN => gettext("Login") ); -} -else -{ - #if user is not know by VHFFS, we return an error - $template = new HTML::Template( filename => $templatedir."/panel/main/lost_failed.tmpl" ); - - $template->param( TEXT_FAILED => gettext("Password recovery failed!") ); - $template->param( TEXT_LOGIN => gettext("Login") ); -} - - -$panel->light( $template ); -$panel->display; Modified: branches/vhffs-design/vhffs-panel/subscribe.pl =================================================================== --- branches/vhffs-design/vhffs-panel/subscribe.pl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/subscribe.pl 2009-05-23 13:44:53 UTC (rev 1402) @@ -40,213 +40,76 @@ use strict; use utf8; use POSIX qw(locale_h); -use CGI; use locale; use Locale::gettext; -use HTML::Template; use Encode; use lib '%VHFFS_LIB_DIR%'; -use Vhffs::User; -use Vhffs::Main; -use Vhffs::Functions; -use Vhffs::Constants; -use Vhffs::Panel::Main; -use Vhffs::Panel::Captcha; +use Vhffs::Panel::Anonymous; -my $panel = new Vhffs::Panel::Main(); +my $panel = new Vhffs::Panel::Anonymous(); exit 0 unless $panel; -my $vhffs = $panel->{'vhffs'}; -my $templatedir = $panel->{'templatedir'}; -my $cgi = $panel->{'cgi'}; +my $vhffs = $panel->{vhffs}; +my $conf = $vhffs->get_config; +my $cgi = $panel->{cgi}; -my $submitted = $cgi->param( 'CREATE_SUBMIT' ); -my @errors = (); -my $template; -my $message; - -my $usecaptcha = Vhffs::Functions::strtobool( $vhffs->get_config->get_panel->{'use_captcha'} ); -my $captchakey = $vhffs->get_config->get_panel->{'captchakey'}; - -if( $vhffs->get_config->get_allow_subscribe == 0 ) -{ - # Subscribe isn't allowed, inform user - $template = new HTML::Template( filename => $templatedir.'/panel/misc/simplemsg.tmpl'); - $template->param( MESSAGE => gettext('You cannot subscribe to VHFFS') ); - $panel->light( $template ); - $panel->display; +if($conf->get_allow_subscribe == 0) { +# Subscription disabled, exit +# TODO Show a nice message exit 0; } +my $vars = {}; -if( defined $submitted ) { -# don't check if form hasn't been submitted +if(defined $cgi->param( 'username' )) { + $panel->validate($cgi, { + 'username' => { regEx => $Vhffs::User::username_regex, + message => gettext( 'Invalid username, it must contain between 3 and 12 alphanumeric characters, all in lowercase' ) }, + 'email' => { regEx => '^.{6,}$', + message => gettext( 'You must declare your mail address') }, + 'firstname' => { regEx => '^[^<>"]+$', + message => gettext( 'Please enter a valid firstname' ) }, + 'lastname' => { regEx => '^[^<>"]+$', + message => gettext( 'Please enter a valid lastname' ) }, + 'address' => { regEx => '\S+', + message => gettext( 'Please enter an address' ) }, + 'zipcode' => { regEx => '^[\w\d\s\-]+$', + message => gettext( 'Please enter a valid zipcode' )}, + 'city' => { regEx => '^[^<>"]+$', + message => gettext( 'Please enter a valid city' ) }, + 'country' => { regEx => '^[^<>"]+$', + message => gettext( 'Please enter a valid country' ) }, + }); - # get filled in parameters - my $mail = $cgi->param( "MAIL" ); - my $username = $cgi->param( "USERNAME" ); - my $firstname = Encode::decode_utf8( $cgi->param( "FIRSTNAME") ); - my $lastname = Encode::decode_utf8( $cgi->param( "LASTNAME" ) ); - my $city = Encode::decode_utf8( $cgi->param("CITY") ); - my $zipcode = Encode::decode_utf8( $cgi->param("ZIPCODE") ); - my $country = Encode::decode_utf8( $cgi->param("COUNTRY") ); - my $address = Encode::decode_utf8( $cgi->param("ADDRESS") ); - - if( $usecaptcha ) { - my $codeuser = $cgi->param('CONFIRMATION'); - my $hexcode = $cgi->param('CODE'); - my $code = pack('H12', $hexcode); - $code ^= pack('H12', $captchakey) if defined $captchakey; - - if( ( ! defined $code ) || ( $codeuser ne $code ) ) - { - push(@errors, {error => gettext("Codes do not match")}); - } + my $mail = Encode::decode_utf8( $cgi->param( 'email') ); + my $username = Encode::decode_utf8( $cgi->param( 'username' ) ); + my $firstname = Encode::decode_utf8( $cgi->param( 'firstname' ) ); + my $lastname = Encode::decode_utf8( $cgi->param( 'lastname' ) ); + my $address = Encode::decode_utf8( $cgi->param( 'address' ) ); + my $zipcode = Encode::decode_utf8( $cgi->param( 'postalcode' ) ); + my $city = Encode::decode_utf8( $cgi->param( 'city' ) ); + my $country = Encode::decode_utf8( $cgi->param( 'country' ) ); + + # We can't do that with our generic method + if(! Vhffs::Functions::valid_mail( $mail ) ) { + $panel->add_error( gettext("You must declare a valid mail address"), + 'email'); } - - if( ! defined $username ) - { - push(@errors, {error => gettext("You must declare your username")}); - } - if( ! Vhffs::User::check_username($username) ) - { - push(@errors, {error => gettext('Invalid username, it must contain between 3 and 12 alphanumeric characters, all in lowercase')}); - } - if( ! defined $country ) - { - push(@errors, {error => gettext("You must declare your country")}); - } - if( ! defined $city ) - { - push(@errors, {error => gettext("You must declare your city")}); - } - if( ! defined $zipcode ) - { - push(@errors, {error => gettext("You must declare your zipcode")}); - } - if( ! defined $firstname ) - { - push(@errors, {error => gettext("You must declare your firstname")}); - } - if( ! defined $lastname ) - { - push(@errors, {error => gettext("You must declare your lastname")}); - } - if( ( ! defined $mail ) || ( length( $mail ) < 6 ) ) - { - push(@errors, {error => gettext("You must declare your mail address")}); - } - if( ! Vhffs::Functions::valid_mail( $mail ) ) - { - push(@errors, {error => gettext("You must declare a valid mail address")}); - } - if( $zipcode !~ /^[\w\d\s\-]+$/ ) - { - push(@errors, {error => gettext("Your zipcode is not correct! Please enter a correct zipcode")}); - } - if( $firstname !~ /^[^<>"]+$/ ) - { - push(@errors, {error => gettext("Please enter a correct firstname")}); - } - if( $lastname !~ /^[^<>"]+$/ ) - { - push(@errors, {error => gettext("Please enter a correct lastname")}); - } - if( $city !~ /^[^<>"]+$/ ) - { - push(@errors, {error => gettext("Please enter a correct city")}); - } - if( $country =~ /^[<>"]+$/ ) - { - push(@errors, {error => gettext("Please enter a correct country")}); - } - - if( ( scalar @errors ) == 0) - { - my $retour; - my $user = Vhffs::User::create( $vhffs, $username, &Vhffs::Functions::generate_random_password(), + + if(! $panel->has_errors()) { + my $user = Vhffs::User::create( $vhffs, $username, &Vhffs::Functions::generate_random_password(), 0, $mail, $firstname, $lastname, $city, $zipcode, $country, $address, ""); - - if(! defined $user ) - { - push( @errors, {error => gettext("Cannot create user, the username you entered already exists")}); - } - else - { - #We set informations user fill in the form - $user->set_status( Vhffs::Constants::WAITING_FOR_CREATION ); - - #Commit all the changes for the current user - if( ( $retour = $user->commit ) < 0 ) - { - push ( @errors, { error => gettext("Cannot apply changes to the user") } ); - } - else - { - my $good_news = gettext("User Successfully created"); - my $good_news2 = gettext("Please wait while we are creating the account, it will take some minutes"); - $template = new HTML::Template( filename => $templatedir."/panel/user/create_complete.tmpl" ); - $template->param( TEXT_BACK => gettext("Back to Login") ); - $template->param( GOOD_NEWS => $good_news ); - $template->param( GOOD_NEWS2 => $good_news2 ); - - Vhffs::Acl::add_acl( $user , $user , Vhffs::Constants::ACL_DELETE , $vhffs ); - Vhffs::Acl::add_acl( $user->get_group , $user , Vhffs::Constants::ACL_DENIED , $vhffs ); - } - } + if(!defined $user) { + $panel->add_error( gettext('Unable to create user, it may be caused by a duplicate username') ); + } else { + $panel->add_info( gettext( 'User successfully created. '. + 'Please wait while we are creating the account, it could take several minutes' ) ); + require 'auth.pl'; # Redirect to login + exit 0; + } } - if ( ( scalar @errors ) > 0 ) { - $template = new HTML::Template( filename => $templatedir."/panel/user/create.tmpl" ); - # There was an error, fill the template parameter - $template->param( ERRORS => \@errors ); - $template->param( USERNAME_VALUE => $username ); - $template->param( MAIL_VALUE => $mail ); - $template->param( FIRSTNAME_VALUE => $firstname ); - $template->param( LASTNAME_VALUE => $lastname ); - $template->param( ZIPCODE_VALUE => $zipcode ); - $template->param( CITY_VALUE => $city ); - $template->param( COUNTRY_VALUE => $country ); - $template->param( ADDRESS_VALUE => $address ); - - } -} else { - $template = new HTML::Template( filename => $templatedir."/panel/user/create.tmpl" ); } -if( ( ! defined $submitted ) || (scalar @errors) != 0 ) { -# $template is defined in every cases - $template->param( TEXT_SUBSCRIBE => gettext("Subscription") ); - $template->param( TEXT_INFOS => gettext("Please fill in all fields, a mail containing your password will be sent to you") ); - $template->param( USERNAME_TEXT => gettext("Username") ); - $template->param( MAIL_TEXT => gettext("mail") ); - $template->param( FIRSTNAME_TEXT => gettext("Firstname") ); - $template->param( LASTNAME_TEXT => gettext("Lastname") ); - $template->param( ZIPCODE_TEXT => gettext("Zipcode") ); - $template->param( CITY_TEXT => gettext("City") ); - $template->param( COUNTRY_TEXT => gettext("Country") ); - $template->param( ADDRESS_TEXT => gettext("Address") ); - $template->param( SEND => gettext("Subscribe") ); - $template->param( BACK => gettext("Back to Login") ); - - $template->param( USECAPTCHA => $usecaptcha ); - if( $usecaptcha ) { - my $captcha = Vhffs::Panel::Captcha->new; - my $code = $captcha->generate_random_string( 6 ); - $code ^= pack('H12', $captchakey) if defined $captchakey; - my $hex = unpack('H12', $code); - $template->param( CODE => $hex ); - - $template->param( CONFIRMATION_TEXT => gettext('Code confirmation') ); - $template->param( REPEAT_CONFIRMATION_TEXT => gettext('Recopy the code') ); - $template->param( CONFIRMATION_ALT => gettext('Confirmation code, contact administrator team if you can\'t read it') ); - $template->param( CONFIRMATION_SOUND_TEXT => gettext('Or listen to the code') ); - } - - $template->param( USERNAME_TIP_TEXT => gettext('Your username. It must contains only alphanumeric characters in lowercase, its length must be between 3 and 12 chars') ); - $template->param( EMAIL_TIP_TEXT => gettext('Your email address. It will be used to contact you when needed and as a destination address if you use our email forwarding service') ); -} - -$panel->light( $template ); -$panel->display; +$panel->render('content/anonymous/subscribe.tt', $vars); Modified: branches/vhffs-design/vhffs-panel/templates/Makefile.am =================================================================== --- branches/vhffs-design/vhffs-panel/templates/Makefile.am 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/Makefile.am 2009-05-23 13:44:53 UTC (rev 1402) @@ -88,9 +88,6 @@ menu/context.tmpl \ menu/context-group.tmpl \ menu/context-modo.tmpl \ - main/lost_failed.tmpl \ - main/lost_ok.tmpl \ - main/lost.tmpl \ main/panel.tmpl \ main/main.tmpl \ menu/main.tmpl \ @@ -119,8 +116,6 @@ git/prefs.tmpl \ git/user_part.tmpl \ user/admin.tmpl \ - user/create_complete.tmpl \ - user/create.tmpl \ user/mailuserspam.tmpl \ user/mailuser.tmpl \ user/mailuservirus.tmpl \ @@ -130,4 +125,8 @@ web/mailuser.tmpl \ web/prefs.tmpl \ cron/create.tmpl \ - cron/prefs.tmpl + cron/prefs.tmpl \ + layouts/anonymous.tt \ + content/anonymous/login.tt \ + content/anonymous/lost-password.tt \ + content/anonymous/subscribe.tt Added: branches/vhffs-design/vhffs-panel/templates/content/anonymous/login.tt =================================================================== --- branches/vhffs-design/vhffs-panel/templates/content/anonymous/login.tt (rev 0) +++ branches/vhffs-design/vhffs-panel/templates/content/anonymous/login.tt 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,16 @@ +[% hosterlink = '<a href="' _ hostersite _ '">' _ hostername _ '</a>' %] +<h1>[% 'Welcome on %s' | i18n | pretty_print(hosterlink) %]</h1> +[% FOREACH e IN errors.global %] +<p class="info">[% e.msg %]</p> +[% END %] +[% FOREACH i IN infos %] +<p class="info">[% i.msg %]</p> +[% END %] +<form name="loginForm" id="loginForm" method="post" action="auth.pl"> +<p><label for="loginUsername">[% 'Username' | i18n %]</label><input type="text" name="username" id="loginUsername" maxlength="50"/></p> +<p><label for="loginPassword">[% 'Password' | i18n %]</label><input type="password" name="password" id="loginPassword"/></p> +<p class="submit"><input type="submit" id="loginSubmit" value="Connexion"/></p> +</form> +[% IF showstats %] +<p id="pinfo">[% 'Woah, %s users and %s groups already trust %s' | i18n | pretty_print(users_count, groups_count, hostername) %]</p> +[% END %] \ No newline at end of file Added: branches/vhffs-design/vhffs-panel/templates/content/anonymous/lost-password.tt =================================================================== --- branches/vhffs-design/vhffs-panel/templates/content/anonymous/lost-password.tt (rev 0) +++ branches/vhffs-design/vhffs-panel/templates/content/anonymous/lost-password.tt 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,12 @@ +<h1>[% 'Password lost' | i18n %]</h1> +<p>[% 'You lost your password? You are a bad guy!' | i18n %]</p> +<p>[% 'But fortunately, we are nice. Just type your username below and we will send you a new password! ' | i18n %]</p> +[% FOREACH e IN errors.global %] +<p class="error">[% e.msg %]</p> +[% END %] +<form id="lostPasswordForm" action="lost.pl" method="post"> +<p><label for="lostPasswordUsername">[% 'Username' | i18n %]</label> + <input type="text" maxlength="12" name="username" id="lostPasswordUsername"/></p> +<p class="submit"><input type="submit" value="[% 'Give me a new password' | i18n %]"/></p> +</form> +<p><a href="auth.pl" class="ajax">[% 'Back to login page' | i18n %]</a></p> \ No newline at end of file Added: branches/vhffs-design/vhffs-panel/templates/content/anonymous/subscribe.tt =================================================================== --- branches/vhffs-design/vhffs-panel/templates/content/anonymous/subscribe.tt (rev 0) +++ branches/vhffs-design/vhffs-panel/templates/content/anonymous/subscribe.tt 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,160 @@ +[% USE CGI %] +[% +# Mandatory to have proper param() return values +# The null filter avoid an "utf-8" echo +CGI.charset('utf-8') | null +%] +[% FOREACH e IN errors.global %] + <p class="error">[% e.msg %]</p> +[% END %] +<form id="subscribeForm" action="subscribe.pl" method="post"> +<p> +<label for="subscribeUsername">[% 'Username' | i18n %]:</label> +<input type="text" id="subscribeUsername" name="username" maxlength="12" value="[% CGI.param('username') | html %]"/> +[% errors.username.0.msg %] +</p> +<p> +<label for="subscribeEmail">[% 'E-Mail' | i18n %]:</label> +<input type="text" id="subscribeEmail" name="email" maxlength="50" value="[% CGI.param('email') | html %]"/> +[% errors.email.0.msg %] +</p> +<p> +<label for="subscribeFirstname">[% 'Firstname' | i18n %]:</label> +<input type="text" id="subscribeFirstname" name="firstname" maxlength="50" value="[% CGI.param('firstname') %]"/> +[% errors.firstname.0.msg %] +</p> +<p> +<label for="subscribeLastname">[% 'Lastname' | i18n %]:</label> +<input type="text" id="subscribeLastname" name="lastname" maxlength="50" value="[% CGI.param('lastname') | html %]"/> +[% errors.lastname.0.msg %] +</p> +<p> +<label for="subscribeAddress">[% 'Address' | i18n %]:</label> +<input type="text" id="subscribeAddress" name="address" maxlength="50" value="[% CGI.param('address') | html %]"/> +[% errors.address.0.msg %] +</p> +<p> +<label for="subscribeZipCode">[% 'Zip code' | i18n %]:</label> +<input type="text" id="subscribeZipCode" name="zipcode" maxlength="10" value="[% CGI.param('zipcode') | html %]"/> +[% errors.zipcode.0.msg %] +</p> +<p> +<label for="subscribeCity">[% 'City' | i18n %]:</label> +<input type="text" id="subscribeCity" name="city" maxlength="50" value="[% CGI.param('city') | html %]"/> +[% errors.city.0.msg %] +</p> +<p> +<label for="subscribeCountry">[% 'Country' | i18n %]</label> +<input type="text" id="subscribeCountry" name="country" maxlength="50" value="[% CGI.param('country') | html %]"/> +[% errors.country.0.msg %] +</p> +<p class="submit"> +<input type="reset" value="[% 'Reset' | i18n %]"/> +<input type="submit" value="[% 'Subscribe' | i18n %]"/> +</p> +</form> + +<script type="text/javascript"> +<!-- + +var Anonymous = {}; + +Anonymous.Subscribe = {}; + +Anonymous.Subscribe.onLoad = function() { + Anonymous.Subscribe.ajaxizeForm(); +} + +Anonymous.Subscribe.ajaxizeForm = function() { + + dojo.require('dijit.form.ValidationTextBox'); + + var widgets = []; + + widgets.push(new dijit.form.ValidationTextBox({ + regExp: '^[a-z0-9]{3,12}$', + required: true, + trim: true, + invalidMessage: 'Invalid username' + }, dojo.byId('subscribeUsername'))); + + widgets.push(new dijit.form.ValidationTextBox({ + regExp: '^.{2,}@.{2,}$', + required: true, + trim: true, + invalidMessage: 'Enter valid email' + }, dojo.byId('subscribeEmail'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter a firstname' + }, dojo.byId('subscribeFirstname'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter a lastname' + }, dojo.byId('subscribeLastname'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter an address' + }, dojo.byId('subscribeAddress'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter a zipcode' + }, dojo.byId('subscribeZipCode'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter a city' + }, dojo.byId('subscribeCity'))); + + widgets.push(new dijit.form.ValidationTextBox({ + required: true, + trim: true, + invalidMessage: 'Enter a country' + }, dojo.byId('subscribeCountry'))); + + var form = dojo.byId('subscribeForm'); + dojo.connect(form, 'onsubmit', function(e) { + dojo.stopEvent(e); + + var valid = true; + dojo.forEach(widgets, function(w) { + // We've to force the blurred attribute + // otherwise validation will fail but + // field won't be marked as bad + w._hasBeenBlurred = true; + if(!w.validate()) { + valid = false; + } + }); + + if(!valid) return; + + var url = dojo.attr(form, 'action'); + var content = dojo.formToObject(form); + var container = dojo.byId('content-panel-anonymous'); + dojo.back.addToHistory(new vhffs.Common.pageState(url, container, content)); + dojo.xhrPost({ + 'url': url, + 'content': content, + load: function(response) { + vhffs.Common.loadContent(container, response); + vhffs.Common.ajaxizeLinks(container); + } + }); + }); + +} + +Anonymous.Subscribe.onLoad(); + +//--> +</script> \ No newline at end of file Added: branches/vhffs-design/vhffs-panel/templates/layouts/anonymous.tt =================================================================== --- branches/vhffs-design/vhffs-panel/templates/layouts/anonymous.tt (rev 0) +++ branches/vhffs-design/vhffs-panel/templates/layouts/anonymous.tt 2009-05-23 13:44:53 UTC (rev 1402) @@ -0,0 +1,44 @@ +<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> +<html xmlns="http://www.w3.org/1999/xhtml" lang="en"> +<head> + <meta http-equiv="content-type" content="text/html; charset=utf-8" /> + <meta name="author" content="VHFFS Team, based on G. Wolfgang original design" /> + <link rel="stylesheet" type="text/css" media="screen,projection" href="/themes/[% theme %]/main.css" /> + <script type="text/javascript" src="/js/dojo/dojo.js"></script> + <script type="text/javascript" src="/js/dijit/dijit.js"></script> + <script type="text/javascript" src="/js/anonymous.js"></script> + <title>Vhffs::Virtual hosting for free software</title> +</head> + +<body> +<div id="background-container"> + <div class="page-container-panel-anonymous"> + <div class="navflag"> + <a href="/?lang=fr_FR"><img class="img-navflag" src="/themes/[% theme %]/img/flag_fr.png" alt="[% 'French' | i18n %]" /></a> + <a href="/?lang=es_ES"><img class="img-navflag" src="/themes/[% theme %]/img/flag_es.png" alt="[% 'Spanish' | i18n %]" /></a> + <a href="/?lang=en_EN"><img class="img-navflag" src="/themes/[% theme %]/img/flag_en.png" alt="[% 'English' | i18n %]" /></a> + </div> + <div class="logo"> + <img src="/themes/[% theme %]/img/vhffs-big.png" alt="Virtual hosting for free software"/> + </div> + <div id="top-menu"> + <ul> +[% IF(subscribe) %] + <li><a href="/subscribe.pl" class="ajax">[% 'Subscribe' | i18n %]</a></li> +[% END %] + <li><a href="/lost.pl" class="ajax">[% 'Lost password' | i18n %]</a></li> +[% IF(public) %] + <li><a href="[% publicurl %]">[% 'Public area' | i18n %]</a></li> +[% END %] + </ul> + </div> + <div id="content-panel-anonymous"> +[% PROCESS $template %] + </div> + <div id="footer"> + <p>[% 'Powered by %s' | i18n | pretty_print('<a href="http://www.vhffs.org">VHFFS</a>') %]</p> + </div> + </div> +</div> +</body> +</html> \ No newline at end of file Deleted: branches/vhffs-design/vhffs-panel/templates/main/lost.tmpl =================================================================== --- branches/vhffs-design/vhffs-panel/templates/main/lost.tmpl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/main/lost.tmpl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,25 +0,0 @@ -<div class="logo"> -</div> - -<div class="misc" id="misc"> - -<h1><TMPL_VAR ESCAPE=1 NAME="TEXT_LOSTPASS"></h1> - -<form action="/lost_ack.pl" method="post" accept-charset="utf-8"> -<h2><TMPL_VAR NAME="TEXT_BLABLA"></h2> -<p> - <label for="username"> - <TMPL_VAR ESCAPE=1 NAME="TEXT_USERNAME"> - </label> - <input type="text" name="username" id="username" maxlength="32"/> -</p> -<p class="button"> - <input type="submit" value="<TMPL_VAR ESCAPE=1 NAME="TEXT_BUTTON">" /> -</p> -</form> - -<p> - <a href="/auth.pl"><TMPL_VAR ESCAPE=1 NAME="TEXT_BACK"></a> -</p> - -</div> Deleted: branches/vhffs-design/vhffs-panel/templates/main/lost_failed.tmpl =================================================================== --- branches/vhffs-design/vhffs-panel/templates/main/lost_failed.tmpl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/main/lost_failed.tmpl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,5 +0,0 @@ -<div class="logo"></div> -<div class="misc" id="misc"> -<h1><TMPL_VAR ESCAPE=1 NAME="TEXT_FAILED"></h1> -<p class="button"><a href="/auth.pl"><TMPL_VAR ESCAPE=1 NAME="TEXT_LOGIN"></a></p> -</div> Deleted: branches/vhffs-design/vhffs-panel/templates/main/lost_ok.tmpl =================================================================== --- branches/vhffs-design/vhffs-panel/templates/main/lost_ok.tmpl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/main/lost_ok.tmpl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,5 +0,0 @@ -<div class="logo"></div> -<div class="misc" id="misc"> -<h1><TMPL_VAR ESCAPE=1 NAME="TEXT_WAITPASS"></h1> -<p class="button"><a href="/auth.pl"><TMPL_VAR ESCAPE=1 NAME="TEXT_LOGIN"></a></p> -</div> Deleted: branches/vhffs-design/vhffs-panel/templates/user/create.tmpl =================================================================== --- branches/vhffs-design/vhffs-panel/templates/user/create.tmpl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/user/create.tmpl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,99 +0,0 @@ -<div class="logo"> -</div> -<div id="subscribe"> - <div id="content"> - <h1><TMPL_VAR ESCAPE=1 NAME="TEXT_SUBSCRIBE"></h1> - <p class="info"><TMPL_VAR ESCAPE=1 NAME="TEXT_INFOS"></p> - <div class="subscribe"> - <form method="post" action="subscribe.pl" accept-charset="utf-8"> - <div id="errors"> - <TMPL_LOOP NAME="ERRORS"> - <p class="error"><TMPL_VAR ESCAPE=1 NAME="ERROR"></p> - </TMPL_LOOP> - </div> - - <p> - <label for="USERNAME"> - <TMPL_VAR ESCAPE=1 NAME="USERNAME_TEXT"> - </label> - <span><input type="text" name="USERNAME" id="USERNAME" maxlength="12" value="<TMPL_VAR ESCAPE=1 NAME="USERNAME_VALUE">" onchange="javascript:check(this.id, validIdentifier, 12);" onkeyup="javascript:check(this.id, validIdentifier, 12);"/> </span> <img src="/themes/<TMPL_VAR ESCAPE=1 NAME="THEME">/images/tip.png" alt="tip" id="username_tip_trigger"/> - </p> - <p> - <label for="MAIL"> - <TMPL_VAR ESCAPE=1 NAME="MAIL_TEXT"> - </label> - <span><input type="text" name="MAIL" id="MAIL" maxlength="200" value="<TMPL_VAR ESCAPE=1 NAME="MAIL_VALUE">" onkeyup="javascript:check(this.id, validEmail);"/> </span> <img src="/themes/<TMPL_VAR ESCAPE=1 NAME="THEME">/images/tip.png" alt="tip" id="email_tip_trigger"/> - </p> - <p> - <label for="FIRSTNAME"> - <TMPL_VAR ESCAPE=1 NAME="FIRSTNAME_TEXT"> - </label> - <span><input type="text" name="FIRSTNAME" id="FIRSTNAME" maxlength="256" value="<TMPL_VAR ESCAPE=1 NAME="FIRSTNAME_VALUE">" onkeyup="javascript:check('FIRSTNAME', validString);" /> </span> - </p> - <p> - <label for="LASTNAME"> - <TMPL_VAR ESCAPE=1 NAME="LASTNAME_TEXT"> - </label> - <span><input type="text" name="LASTNAME" id="LASTNAME" maxlength="256" value="<TMPL_VAR ESCAPE=1 NAME="LASTNAME_VALUE">" onkeyup="javascript:check('LASTNAME', validString);"/> </span> - </p> - <p> - <label for="ADDRESS"> - <TMPL_VAR ESCAPE=1 NAME="ADDRESS_TEXT"> - </label> - <span><input type="text" name="ADDRESS" id="ADDRESS" maxlength="512" value="<TMPL_VAR ESCAPE=1 NAME="ADDRESS_VALUE">" onkeyup="javascript:check('ADDRESS', validString);"/> </span> - </p> - <p> - <label for="CITY"> - <TMPL_VAR ESCAPE=1 NAME="CITY_TEXT"> - </label> - <span><input type="text" name="CITY" id="CITY" maxlength="64" value="<TMPL_VAR ESCAPE=1 NAME="CITY_VALUE">" onkeyup="javascript:check('CITY', validString);"/> </span> - </p> - <p> - <label for="COUNTRY"> - <TMPL_VAR ESCAPE=1 NAME="COUNTRY_TEXT"> - </label> - <span><input type="text" name="COUNTRY" id="COUNTRY" maxlength="32" value="<TMPL_VAR ESCAPE=1 NAME="COUNTRY_VALUE">" onkeyup="javascript:check('COUNTRY', validString);"/> </span> - </p> - <p> - <label for="ZIPCODE"> - <TMPL_VAR ESCAPE=1 NAME="ZIPCODE_TEXT"> - </label> - <span><input type="text" name="ZIPCODE" id="ZIPCODE" maxlength="16" value="<TMPL_VAR ESCAPE=1 NAME="ZIPCODE_VALUE">" onkeyup="javascript:check(this.id, validZip);" onchange="javascript:check(this.id, validZip);"/> </span> - </p> -<TMPL_IF NAME="USECAPTCHA"> - <p> - <label for="CONFIRMATION"> - <TMPL_VAR ESCAPE=1 NAME="CONFIRMATION_TEXT"> - </label> - <img src="show_code.pl?code=<TMPL_VAR ESCAPE=1 NAME="CODE">" alt="<TMPL_VAR ESCAPE=1 NAME="CONFIRMATION_ALT">"/> <a href="play_code.pl?code=<TMPL_VAR ESCAPE=1 NAME="CODE">"><TMPL_VAR ESCAPE=1 NAME="CONFIRMATION_SOUND_TEXT"></a> - </p> - <p> - <label for="CONFIRMATION"> - <TMPL_VAR ESCAPE=1 NAME="REPEAT_CONFIRMATION_TEXT"> - </label> - <input type="text" name="CONFIRMATION" id="CONFIRMATION" maxlength="16"/> - </p> - <input type="hidden" name="CODE" id="CODE" value="<TMPL_VAR ESCAPE=1 NAME="CODE">"/> -</TMPL_IF> - <p class="button"> - <input type="submit" value="<TMPL_VAR ESCAPE=1 NAME="SEND">" name="CREATE_SUBMIT"/> - </p> - </form> - </div> - <p class="home"><a href="/auth.pl"><TMPL_VAR ESCAPE=1 NAME="BACK"></a></p> - </div> - <div id="email_tooltip" class="tooltip"><TMPL_VAR ESCAPE=1 NAME="EMAIL_TIP_TEXT"></div> - <div id="username_tooltip" class="tooltip"><TMPL_VAR ESCAPE=1 NAME="USERNAME_TIP_TEXT"></div> - <script type="text/javascript"> - new Tooltip('username_tip_trigger', 'username_tooltip', { delta_x: 5, delta_y: 5 }); - new Tooltip('email_tip_trigger', 'email_tooltip', { delta_x: 5, delta_y: 5 }); - check('USERNAME', validIdentifier, 12); - check('MAIL', validEmail); - check('FIRSTNAME', validString); - check('LASTNAME', validString); - check('ADDRESS', validString); - check('CITY', validString); - check('COUNTRY', validString); - check('ZIPCODE', validZip); - </script> -</div> Deleted: branches/vhffs-design/vhffs-panel/templates/user/create_complete.tmpl =================================================================== --- branches/vhffs-design/vhffs-panel/templates/user/create_complete.tmpl 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-panel/templates/user/create_complete.tmpl 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,8 +0,0 @@ -<div class="logo"></div> -<div class="login"> -<h1><TMPL_VAR ESCAPE=1 NAME="TITLE"></h1> -<h2><TMPL_VAR ESCAPE=1 NAME="GOOD_NEWS"></h2> -<h2><TMPL_VAR ESCAPE=1 NAME="GOOD_NEWS2"></h2> -<h2 class="error"><TMPL_VAR ESCAPE=1 NAME="BAD_NEWS"></h2> -<p class="button"><a href="/auth.pl"><TMPL_VAR ESCAPE=1 NAME="TEXT_BACK"></a></p> -</div> Modified: branches/vhffs-design/vhffs-themes/Makefile.am =================================================================== --- branches/vhffs-design/vhffs-themes/Makefile.am 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-themes/Makefile.am 2009-05-23 13:44:53 UTC (rev 1402) @@ -82,6 +82,9 @@ light-grey/img/loading.gif \ light-grey/img/vhffs.png \ light-grey/img/bullet.png \ + light-grey/img/warning.png \ + light-grey/img/tooltipConnectorLeft.png \ + light-grey/img/popupMenuBg.gif \ light-grey/img/background_body.png \ light-grey/img/background_layout_3.gif Added: branches/vhffs-design/vhffs-themes/light-grey/img/popupMenuBg.gif =================================================================== (Binary files differ) Property changes on: branches/vhffs-design/vhffs-themes/light-grey/img/popupMenuBg.gif ___________________________________________________________________ Name: svn:mime-type + application/octet-stream Added: branches/vhffs-design/vhffs-themes/light-grey/img/tooltipConnectorLeft.png =================================================================== (Binary files differ) Property changes on: branches/vhffs-design/vhffs-themes/light-grey/img/tooltipConnectorLeft.png ___________________________________________________________________ Name: svn:mime-type + application/octet-stream Added: branches/vhffs-design/vhffs-themes/light-grey/img/warning.png =================================================================== (Binary files differ) Property changes on: branches/vhffs-design/vhffs-themes/light-grey/img/warning.png ___________________________________________________________________ Name: svn:mime-type + application/octet-stream Modified: branches/vhffs-design/vhffs-themes/light-grey/main.css =================================================================== --- branches/vhffs-design/vhffs-themes/light-grey/main.css 2009-05-23 13:41:01 UTC (rev 1401) +++ branches/vhffs-design/vhffs-themes/light-grey/main.css 2009-05-23 13:44:53 UTC (rev 1402) @@ -1,3 +1,1358 @@ +/* Dijit original styles, + * Pasted from dijit/themes/dijit.js + * We override some of them later + */ + +.dijitReset { + + margin:0; + border:0; + padding:0; + line-height:normal; + font: inherit; + color: inherit; +} +.dijitInline { + + display:-moz-inline-box; + display:inline-block; + #zoom: 1; + #display:inline; + border:0; + padding:0; + vertical-align:middle; + #vertical-align: auto; +} +.dijitHidden { + + display: none !important; +} +.dijitVisible { + + display: block !important; + position: relative; +} +.dj_ie INPUT.dijitTextBox, +.dj_ie .dijitInputField INPUT { + font-size: 100%; +} +.dj_ie .dijitInputField INPUT { + margin: -1px 0 !important; +} +.dj_iequirks .dijitInputField INPUT { + margin-top: -3px !important; +} +.dijitInlineTable { + + display: -moz-inline-stack; + display:inline-table; + display:inline-block; + #zoom: 1; + #display:inline; + box-sizing: content-box; -moz-box-sizing: content-box; + border:0; + padding:0; +} +.dijitTeeny { + font-size:1px; + line-height:1px; +} +.dijitPopup { + position: absolute; + background-color: transparent; + margin: 0; + border: 0; + padding: 0; +} +.dijit_a11y .dijitPopup, +.dijit_ally .dijitPopup div, +.dijit_a11y .dijitPopup table, +.dijit_a11y .dijitTooltipContainer { + background-color: white !important; +} +.dijitInputField { + overflow:hidden; + #zoom:1; +} +.dijitPositionOnly { + + padding: 0 !important; + border: 0 !important; + background-color: transparent !important; + background-image: none !important; + height: auto !important; + width: auto !important; +} +.dijitNonPositionOnly { + + float: none !important; + position: static !important; + margin: 0 0 0 0 !important; + vertical-align: middle !important; +} +.dijitBackgroundIframe { + + position: absolute; + left: 0; + top: 0; + width: 100%; + height: 100%; + z-index: -1; + border: 0; + padding: 0; + margin: 0; +} +.dijitClickableRegion { + + background-color: #e2ebf2; + cursor: text; +} +.dijitDisplayNone { + + display:none !important; +} +.dijitContainer { + + overflow: hidden; +} +.dijit_a11y * { + background-image:none !important; +} +.dijit_a11y .dijitCalendarIncrementControl { + display: none; +} +.dijit_a11y .dijitA11ySideArrow { + display: inline !important; + cursor: pointer; +} +.dijit_a11y .dijitCalendarSelectedDate { + text-decoration:overline !important; +} +.dijit_a11y .dijit * { + background:white !important; + color:black !important; +} +.dijit_a11y .dijitButtonNode { + border-color: black!important; + border-style: outset!important; + border-width: medium!important; +} +.dijit_a11y .dijitButtonDisabled .dijitButtonNode, +.dijit_a11y .dijitDropDownButtonDisabled .dijitButtonNode, +.dijit_a11y .dijitComboButtonDisabled .dijitButtonNode, +.dijit_a11y .dijitComboBoxDisabled .dijitInputField, +.dijit_a11y .dijitComboBoxDisabled .dijitButtonNode, +.dijit_a11y .dijitSpinnerDisabled .dijitButtonNode, +.dijit_a11y .dijitSpinnerDisabled .dijitInputField { + border-style: outset!important; + border-width: medium!important; + border-color: #999 !important; + color:#999 !important; +} +.dj_ff2 .dijit_a11y .dijitComboButton .dijitButtonContentsFocused, +.dj_ff2 .dijit_a11y .dijitComboButton .dijitDownArrowButtonFocused { + border: 1px dotted black !important; +} +.dijitButtonNode * { + vertical-align: middle; +} +.dijit_a11y .dijitArrowButtonInner { + width: 1em; + display: none !important; +} +.dijitButtonNode .dijitArrowButtonInner { + background:no-repeat center; + width: 16px; +} +.dijitComboBox .dijitArrowButtonInner { + display: block; +} +.dijit_a11y .dijitToggleButtonChecked .dijitToggleButtonIconChar { + display: inline !important; +} + +.dijitLeft { + + background-position:left top; + background-repeat:no-repeat; +} +.dijitStretch { + + white-space:nowrap; + background-repeat:repeat-x; +} +.dijitRight { + + #display:inline; + background-position:right top; + background-repeat:no-repeat; +} +.dijitButton, +.dijitDropDownButton, +.dijitComboButton { + + margin: 0.2em; +} +.dijitToolbar .dijitButton, +.dijitToolbar .dijitDropDownButton, +.dijitToolbar .dijitComboButton { + margin: 0; +} +.dj_ie8 .dijitToolbar button, +.dj_webkit .dijitToolbar button { + + padding: 1px 2px; +} +.dj_ie .dijitToolbar .dijitComboBox{ + + vertical-align: middle; +} +.dj_ie .dijitComboButton { + + margin-bottom: -3px; +} +.dj_webkit .dijitToolbar .dijitDropDownButton { + padding-left: 0.3em; +} +.dj_gecko .dijitToolbar .dijitButtonNode::-moz-focus-inner { + padding:0; +} +.dijitButtonNode { + + border:1px solid gray; + margin:0; + line-height:normal; + vertical-align: middle; + #vertical-align: auto; + text-align:center; + white-space: nowrap; +} +.dijitButtonNode, .dijitButtonNode * { + cursor: pointer; +} +.dijitReadOnly *, +.dijitDisabled *, +.dijitReadOnly, +.dijitDisabled, +.dijitDisabledClickableRegion { + cursor: not-allowed !important; +} +.dj_ie .dijitButtonNode { + + zoom: 1; +} +.dj_ie .dijitButtonNode button { + + overflow: visible; +} +.dijitArrowButton { + + + padding: 0 .4em; +} +DIV.dijitArrowButton { + float: right; +} +.dijitSpinner .dijitInputLayoutContainer .dijitArrowButton { + border-style: solid; + border-width: 0 0 0 1px !important; + padding: 0; + position: absolute; + right: 0; + float: none; +} +.dijitSpinner .dijitInputLayoutContainer .dijitArrowButton { + position: absolute; + height: 50%; +} +.dijitSpinner .dijitInputLayoutContainer .dijitDownArrowButton { + top: auto; + bottom: 0; + border-top-width: 1px !important; +} +.dijitSpinner .dijitInputLayoutContainer .dijitUpArrowButton { + top: 0; + bottom: auto; +} +TABLE.dijitComboButton { + + border-collapse: collapse; + border:0; + padding:0; + margin:0; +} +.dijitToolbar .dijitComboButton { + + border-collapse: separate; +} +.dj_ie BUTTON.dijitButtonNode { + overflow: visible; +} +table .dijitButton .dijitButtonNode, +table .dijitComboButton .dijitButtonNode { + #overflow:hidden; +} +.dijitButtonNode IMG { + + vertical-align:middle; + +} +.dijitTextBox, +.dijitComboBox, +.dijitSpinner { + border: solid black 1px; + #overflow: hidden; + width: 15em; + vertical-align: middle; + #vertical-align: auto; +} +.dijitTimeTextBox { + width: 8em; +} +.dijitTextBox input:focus, +.dijitComboBox input:focus, +.dijitSpinner input:focus { + outline: none; +} +.dijitTextBoxFocused, +.dijitComboBoxFocused, +.dijitSpinnerFocused, .dijitSpinnerUpArrowActive, .dijitSpinnerDownArrowActive, +.dijitTextAreaFocused { + + outline: auto 5px -webkit-focus-ring-color; +} +.dijitTextAreaFocused div { + + outline: none !important; +} +.dijitTextBox INPUT, +.dijitComboBox INPUT, +.dijitSpinner INPUT { + border-left: solid black 1px; + display:inline; + position:static !important; + border:0 !important; + margin:0 !important; + vertical-align:top !important; + background-color:transparent !important; + background-image:none !important; + width:100% !important; +} +.dijitValidationIcon { + visibility: hidden; + display: block; + padding: 0 2px; + float: right; + height: auto; +} +.dijitValidationIconText { + visibility: hidden; + display: none; + float:right; + font-family: sans-serif; + font-style:italic; + font-size: 0.75em; + padding-right: 0.15em; + line-height: 160%; +} +.dijit_a11y .dijitValidationIcon { display: none !important; } +.dijit_a11y .dijitValidationIconText { display: block !important; } +.dijitError .dijitValidationIcon, +.dijitError .dijitValidationIconText { + visibility: visible; +} +.dijitTextBox .dijitArrowButton { + + display:none; +} +.dijitCheckBox, +.dijitRadio, +.dijitCheckBoxInput { + padding: 0; + border: 0; + width: 16px; + height: 16px; + background-position:center center; + background-repeat:no-repeat; + overflow: hidden; +} +.dijitCheckBox INPUT, +.dijitRadio INPUT { + margin: 0; + padding: 0; + display: block; +} +.dijitCheckBoxInput { + + opacity: 0.01; +} +.dj_ie .dijitCheckBoxInput { + filter: alpha(opacity=0); +} +.dijit_a11y .dijitCheckBox, +.dijit_a11y .dijitRadio { + width: auto; + height: auto; +} +.dijit_a11y .dijitCheckBoxInput { + opacity: 1; + filter: none; + width: auto; + height: auto; +} +.dijitProgressBarEmpty{ + + position:relative;overflow:hidden; + border:1px solid black; + z-index:0; +} +.dijitProgressBarFull { + + position:absolute; + overflow:hidden; + z-index:-1; + top:0; + width:100%; +} +.dj_ie6 .dijitProgressBarFull { + height:1.6em; +} +.dijitProgressBarTile { + + position:absolute; + overflow:hidden; + top:0; + left:0; + bottom:0; + right:0; + margin:0; + padding:0; + width:auto; + height:auto; + background-color:#aaa; + background-attachment: fixed; +} +.dijit_a11y .dijitProgressBarTile{ + + border-width:4px; + border-style:solid; + background-color:transparent !important; +} +.dj_ie6 .dijitProgressBarTile { + + position:static; + + height:1.6em; +} +.dijitProgressBarIndeterminate .dijitProgressBarLabel { + visibility:hidden; +} +.dijitProgressBarIndeterminate .dijitProgressBarTile { + +} +.dijitProgressBarIndeterminateHighContrastImage { + display:none; +} +.dijit_a11y .dijitProgressBarIndeterminate .dijitProgressBarIndeterminateHighContrastImage { + display:block; + position:absolute; + top:0; + bottom:0; + margin:0; + padding:0; + width:100%; + height:auto; +} +.dijitProgressBarLabel { + display:block; + position:static; + width:100%; + text-align:center; + background-color:transparent !important; +} +.dijitTooltip { + position: absolute; + z-index: 2000; + display: block; + + left: 50%; + top: -10000px; + overflow: visible; +} +.dijitTooltipContainer { + border: solid black 2px; + background: #b8b5b5; + color: black; + font-size: small; +} +.dijitTooltipFocusNode { + padding: 2px 2px 2px 2px; +} +.dijitTooltipConnector { + position: absolute; +} +.dijitTooltipData { + display:none; +} +.dijitLayoutContainer{ + position: relative; + display: block; + overflow: hidden; +} +body .dijitAlignTop, +body .dijitAlignBottom, +body .dijitAlignLeft, +body .dijitAlignRight { + position: absolute; + overflow: hidden; +} +body .dijitAlignClient { position: absolute; } +.dijitBorderContainer, .dijitBorderContainerNoGutter { + position:relative; + overflow: hidden; +} +.dijitBorderContainerPane, +.dijitBorderContainerNoGutterPane { + position: absolute !important; + z-index: 2; +} +.dijitBorderContainer > .dijitTextArea { + + resize: none; +} +.dijitGutter { + + position: absolute; + font-size: 1px; +} +.dijitSplitter { + position: absolute; + overflow: hidden; + z-index: 10; + background-color: #fff; + border-color: gray; + border-style: solid; + border-width: 0; +} +.