| [ Index ] |
PHP Cross Reference of Drupal 6 (gatewave) |
[Summary view] [Print] [Text view]
1 /* 2 * jQuery UI Accordion 1.6 3 * 4 * Copyright (c) 2008 AUTHORS.txt (http://ui.jquery.com/about) 5 * Dual licensed under the MIT (MIT-LICENSE.txt) 6 * and GPL (GPL-LICENSE.txt) licenses. 7 * 8 * http://docs.jquery.com/UI/Accordion 9 * 10 * Depends: 11 * ui.core.js 12 */ 13 (function($) { 14 15 $.widget("ui.accordion", { 16 17 _init: function() { 18 var options = this.options; 19 20 if ( options.navigation ) { 21 var current = this.element.find("a").filter(options.navigationFilter); 22 if ( current.length ) { 23 if ( current.filter(options.header).length ) { 24 options.active = current; 25 } else { 26 options.active = current.parent().parent().prev(); 27 current.addClass("current"); 28 } 29 } 30 } 31 32 // calculate active if not specified, using the first header 33 options.headers = this.element.find(options.header); 34 options.active = findActive(options.headers, options.active); 35 36 // IE7-/Win - Extra vertical space in Lists fixed 37 if ($.browser.msie) { 38 this.element.find('a').css('zoom', '1'); 39 } 40 41 if (!this.element.hasClass("ui-accordion")) { 42 this.element.addClass("ui-accordion"); 43 $('<span class="ui-accordion-left"></span>').insertBefore(options.headers); 44 $('<span class="ui-accordion-right"></span>').appendTo(options.headers); 45 options.headers.addClass("ui-accordion-header"); 46 } 47 48 var maxHeight; 49 if ( options.fillSpace ) { 50 maxHeight = this.element.parent().height(); 51 options.headers.each(function() { 52 maxHeight -= $(this).outerHeight(); 53 }); 54 var maxPadding = 0; 55 options.headers.next().each(function() { 56 maxPadding = Math.max(maxPadding, $(this).innerHeight() - $(this).height()); 57 }).height(maxHeight - maxPadding); 58 } else if ( options.autoHeight ) { 59 maxHeight = 0; 60 options.headers.next().each(function() { 61 maxHeight = Math.max(maxHeight, $(this).outerHeight()); 62 }).height(maxHeight); 63 } 64 65 this.element.attr('role','tablist'); 66 67 var self=this; 68 options.headers 69 .attr('role','tab') 70 .bind('keydown', function(event) { return self._keydown(event); }) 71 .next() 72 .attr('role','tabpanel'); 73 74 options.headers 75 .not(options.active || "") 76 .attr('aria-expanded','false') 77 .attr("tabIndex", "-1") 78 .next() 79 .hide(); 80 81 // make sure at least one header is in the tab order 82 if (!options.active.length) { 83 options.headers.eq(0).attr('tabIndex','0'); 84 } else { 85 options.active 86 .attr('aria-expanded','true') 87 .attr("tabIndex", "0") 88 .parent().andSelf().addClass(options.selectedClass); 89 } 90 91 // only need links in taborder for Safari 92 if (!$.browser.safari) 93 options.headers.find('a').attr('tabIndex','-1'); 94 95 if (options.event) { 96 this.element.bind((options.event) + ".accordion", clickHandler); 97 } 98 }, 99 100 destroy: function() { 101 this.options.headers.parent().andSelf().removeClass(this.options.selectedClass); 102 this.options.headers.prev(".ui-accordion-left").remove(); 103 this.options.headers.children(".ui-accordion-right").remove(); 104 this.options.headers.next().css("display", ""); 105 if ( this.options.fillSpace || this.options.autoHeight ) { 106 this.options.headers.next().css("height", ""); 107 } 108 $.removeData(this.element[0], "accordion"); 109 110 this.element.removeClass("ui-accordion").unbind(".accordion"); 111 }, 112 113 _keydown: function(event) { 114 if (this.options.disabled || event.altKey || event.ctrlKey) 115 return; 116 117 var keyCode = $.ui.keyCode; 118 119 var length = this.options.headers.length; 120 var currentIndex = this.options.headers.index(event.target); 121 var toFocus = false; 122 123 switch(event.keyCode) { 124 case keyCode.RIGHT: 125 case keyCode.DOWN: 126 toFocus = this.options.headers[(currentIndex + 1) % length]; 127 break; 128 case keyCode.LEFT: 129 case keyCode.UP: 130 toFocus = this.options.headers[(currentIndex - 1 + length) % length]; 131 break; 132 case keyCode.SPACE: 133 case keyCode.ENTER: 134 return clickHandler.call(this.element[0], { target: event.target }); 135 } 136 137 if (toFocus) { 138 $(event.target).attr('tabIndex','-1'); 139 $(toFocus).attr('tabIndex','0'); 140 toFocus.focus(); 141 return false; 142 } 143 144 return true; 145 }, 146 147 activate: function(index) { 148 // call clickHandler with custom event 149 clickHandler.call(this.element[0], { 150 target: findActive( this.options.headers, index )[0] 151 }); 152 } 153 154 }); 155 156 function scopeCallback(callback, scope) { 157 return function() { 158 return callback.apply(scope, arguments); 159 }; 160 }; 161 162 function completed(cancel) { 163 // if removed while animated data can be empty 164 if (!$.data(this, "accordion")) { 165 return; 166 } 167 168 var instance = $.data(this, "accordion"); 169 var options = instance.options; 170 options.running = cancel ? 0 : --options.running; 171 if ( options.running ) { 172 return; 173 } 174 if ( options.clearStyle ) { 175 options.toShow.add(options.toHide).css({ 176 height: "", 177 overflow: "" 178 }); 179 } 180 instance._trigger('change', null, options.data); 181 } 182 183 function toggle(toShow, toHide, data, clickedActive, down) { 184 var options = $.data(this, "accordion").options; 185 options.toShow = toShow; 186 options.toHide = toHide; 187 options.data = data; 188 var complete = scopeCallback(completed, this); 189 190 $.data(this, "accordion")._trigger("changestart", null, options.data); 191 192 // count elements to animate 193 options.running = toHide.size() === 0 ? toShow.size() : toHide.size(); 194 195 if ( options.animated ) { 196 var animOptions = {}; 197 198 if ( !options.alwaysOpen && clickedActive ) { 199 animOptions = { 200 toShow: $([]), 201 toHide: toHide, 202 complete: complete, 203 down: down, 204 autoHeight: options.autoHeight 205 }; 206 } else { 207 animOptions = { 208 toShow: toShow, 209 toHide: toHide, 210 complete: complete, 211 down: down, 212 autoHeight: options.autoHeight 213 }; 214 } 215 216 if (!options.proxied) { 217 options.proxied = options.animated; 218 } 219 220 if (!options.proxiedDuration) { 221 options.proxiedDuration = options.duration; 222 } 223 224 options.animated = $.isFunction(options.proxied) ? 225 options.proxied(animOptions) : options.proxied; 226 227 options.duration = $.isFunction(options.proxiedDuration) ? 228 options.proxiedDuration(animOptions) : options.proxiedDuration; 229 230 var animations = $.ui.accordion.animations, 231 duration = options.duration, 232 easing = options.animated; 233 234 if (!animations[easing]) { 235 animations[easing] = function(options) { 236 this.slide(options, { 237 easing: easing, 238 duration: duration || 700 239 }); 240 }; 241 } 242 243 animations[easing](animOptions); 244 245 } else { 246 if ( !options.alwaysOpen && clickedActive ) { 247 toShow.toggle(); 248 } else { 249 toHide.hide(); 250 toShow.show(); 251 } 252 complete(true); 253 } 254 toHide.prev().attr('aria-expanded','false').attr("tabIndex", "-1"); 255 toShow.prev().attr('aria-expanded','true').attr("tabIndex", "0").focus();; 256 } 257 258 function clickHandler(event) { 259 var options = $.data(this, "accordion").options; 260 if (options.disabled) { 261 return false; 262 } 263 264 // called only when using activate(false) to close all parts programmatically 265 if ( !event.target && !options.alwaysOpen ) { 266 options.active.parent().andSelf().toggleClass(options.selectedClass); 267 var toHide = options.active.next(), 268 data = { 269 options: options, 270 newHeader: $([]), 271 oldHeader: options.active, 272 newContent: $([]), 273 oldContent: toHide 274 }, 275 toShow = (options.active = $([])); 276 toggle.call(this, toShow, toHide, data ); 277 return false; 278 } 279 // get the click target 280 var clicked = $(event.target); 281 282 // due to the event delegation model, we have to check if one 283 // of the parent elements is our actual header, and find that 284 // otherwise stick with the initial target 285 clicked = $( clicked.parents(options.header)[0] || clicked ); 286 287 var clickedActive = clicked[0] == options.active[0]; 288 289 // if animations are still active, or the active header is the target, ignore click 290 if (options.running || (options.alwaysOpen && clickedActive)) { 291 return false; 292 } 293 if (!clicked.is(options.header)) { 294 return; 295 } 296 297 // switch classes 298 options.active.parent().andSelf().toggleClass(options.selectedClass); 299 if ( !clickedActive ) { 300 clicked.parent().andSelf().addClass(options.selectedClass); 301 } 302 303 // find elements to show and hide 304 var toShow = clicked.next(), 305 toHide = options.active.next(), 306 data = { 307 options: options, 308 newHeader: clickedActive && !options.alwaysOpen ? $([]) : clicked, 309 oldHeader: options.active, 310 newContent: clickedActive && !options.alwaysOpen ? $([]) : toShow, 311 oldContent: toHide 312 }, 313 down = options.headers.index( options.active[0] ) > options.headers.index( clicked[0] ); 314 315 options.active = clickedActive ? $([]) : clicked; 316 toggle.call(this, toShow, toHide, data, clickedActive, down ); 317 318 return false; 319 }; 320 321 function findActive(headers, selector) { 322 return selector 323 ? typeof selector == "number" 324 ? headers.filter(":eq(" + selector + ")") 325 : headers.not(headers.not(selector)) 326 : selector === false 327 ? $([]) 328 : headers.filter(":eq(0)"); 329 } 330 331 $.extend($.ui.accordion, { 332 version: "1.6", 333 defaults: { 334 autoHeight: true, 335 alwaysOpen: true, 336 animated: 'slide', 337 event: "click", 338 header: "a", 339 navigationFilter: function() { 340 return this.href.toLowerCase() == location.href.toLowerCase(); 341 }, 342 running: 0, 343 selectedClass: "selected" 344 }, 345 animations: { 346 slide: function(options, additions) { 347 options = $.extend({ 348 easing: "swing", 349 duration: 300 350 }, options, additions); 351 if ( !options.toHide.size() ) { 352 options.toShow.animate({height: "show"}, options); 353 return; 354 } 355 var hideHeight = options.toHide.height(), 356 showHeight = options.toShow.height(), 357 difference = showHeight / hideHeight, 358 padding = options.toShow.outerHeight() - options.toShow.height(), 359 margin = options.toShow.css('marginBottom'), 360 overflow = options.toShow.css('overflow') 361 tmargin = options.toShow.css('marginTop'); 362 options.toShow.css({ height: 0, overflow: 'hidden', marginTop: 0, marginBottom: -padding }).show(); 363 options.toHide.filter(":hidden").each(options.complete).end().filter(":visible").animate({height:"hide"},{ 364 step: function(now) { 365 var current = (hideHeight - now) * difference; 366 if ($.browser.msie || $.browser.opera) { 367 current = Math.ceil(current); 368 } 369 options.toShow.height( current ); 370 }, 371 duration: options.duration, 372 easing: options.easing, 373 complete: function() { 374 if ( !options.autoHeight ) { 375 options.toShow.css("height", "auto"); 376 } 377 options.toShow.css({marginTop: tmargin, marginBottom: margin, overflow: overflow}); 378 options.complete(); 379 } 380 }); 381 }, 382 bounceslide: function(options) { 383 this.slide(options, { 384 easing: options.down ? "easeOutBounce" : "swing", 385 duration: options.down ? 1000 : 200 386 }); 387 }, 388 easeslide: function(options) { 389 this.slide(options, { 390 easing: "easeinout", 391 duration: 700 392 }); 393 } 394 } 395 }); 396 397 })(jQuery);
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
| Generated: Thu Mar 24 11:18:33 2011 | Cross-referenced by PHPXref 0.7 |