| [ Index ] |
PHP Cross Reference of WordPress |
[Summary view] [Print] [Text view]
1 /** 2 * Pointer jQuery widget. 3 */ 4 (function($){ 5 var identifier = 0, 6 zindex = 9999; 7 8 $.widget("wp.pointer", { 9 options: { 10 pointerClass: 'wp-pointer', 11 pointerWidth: 320, 12 content: function( respond, event, t ) { 13 return $(this).text(); 14 }, 15 buttons: function( event, t ) { 16 var close = ( wpPointerL10n ) ? wpPointerL10n.dismiss : 'Dismiss', 17 button = $('<a class="close" href="#">' + close + '</a>'); 18 19 return button.bind( 'click.pointer', function(e) { 20 e.preventDefault(); 21 t.element.pointer('close'); 22 }); 23 }, 24 position: 'top', 25 show: function( event, t ) { 26 t.pointer.show(); 27 t.opened(); 28 }, 29 hide: function( event, t ) { 30 t.pointer.hide(); 31 t.closed(); 32 }, 33 document: document 34 }, 35 36 _create: function() { 37 var positioning, 38 family; 39 40 this.content = $('<div class="wp-pointer-content"></div>'); 41 this.arrow = $('<div class="wp-pointer-arrow"><div class="wp-pointer-arrow-inner"></div></div>'); 42 43 family = this.element.parents().add( this.element ); 44 positioning = 'absolute'; 45 46 if ( family.filter(function(){ return 'fixed' === $(this).css('position'); }).length ) 47 positioning = 'fixed'; 48 49 this.pointer = $('<div />') 50 .append( this.content ) 51 .append( this.arrow ) 52 .attr('id', 'wp-pointer-' + identifier++) 53 .addClass( this.options.pointerClass ) 54 .css({'position': positioning, 'width': this.options.pointerWidth+'px', 'display': 'none'}) 55 .appendTo( this.options.document.body ); 56 }, 57 58 _setOption: function( key, value ) { 59 var o = this.options, 60 tip = this.pointer; 61 62 // Handle document transfer 63 if ( key === "document" && value !== o.document ) { 64 tip.detach().appendTo( value.body ); 65 66 // Handle class change 67 } else if ( key === "pointerClass" ) { 68 tip.removeClass( o.pointerClass ).addClass( value ); 69 } 70 71 // Call super method. 72 $.Widget.prototype._setOption.apply( this, arguments ); 73 74 // Reposition automatically 75 if ( key === "position" ) { 76 this.reposition(); 77 78 // Update content automatically if pointer is open 79 } else if ( key === "content" && this.active ) { 80 this.update(); 81 } 82 }, 83 84 destroy: function() { 85 this.pointer.remove(); 86 $.Widget.prototype.destroy.call( this ); 87 }, 88 89 widget: function() { 90 return this.pointer; 91 }, 92 93 update: function( event ) { 94 var self = this, 95 o = this.options, 96 dfd = $.Deferred(), 97 content; 98 99 if ( o.disabled ) 100 return; 101 102 dfd.done( function( content ) { 103 self._update( event, content ); 104 }) 105 106 // Either o.content is a string... 107 if ( typeof o.content === 'string' ) { 108 content = o.content; 109 110 // ...or o.content is a callback. 111 } else { 112 content = o.content.call( this.element[0], dfd.resolve, event, this._handoff() ); 113 } 114 115 // If content is set, then complete the update. 116 if ( content ) 117 dfd.resolve( content ); 118 119 return dfd.promise(); 120 }, 121 122 /** 123 * Update is separated into two functions to allow events to defer 124 * updating the pointer (e.g. fetch content with ajax, etc). 125 */ 126 _update: function( event, content ) { 127 var buttons, 128 o = this.options; 129 130 if ( ! content ) 131 return; 132 133 this.pointer.stop(); // Kill any animations on the pointer. 134 this.content.html( content ); 135 136 buttons = o.buttons.call( this.element[0], event, this._handoff() ); 137 if ( buttons ) { 138 buttons.wrap('<div class="wp-pointer-buttons" />').parent().appendTo( this.content ); 139 } 140 141 this.reposition(); 142 }, 143 144 reposition: function() { 145 var position; 146 147 if ( this.options.disabled ) 148 return; 149 150 position = this._processPosition( this.options.position ); 151 152 // Reposition pointer. 153 this.pointer.css({ 154 top: 0, 155 left: 0, 156 zIndex: zindex++ // Increment the z-index so that it shows above other opened pointers. 157 }).show().position($.extend({ 158 of: this.element, 159 collision: 'fit none' 160 }, position )); // the object comes before this.options.position so the user can override position.of. 161 162 this.repoint(); 163 }, 164 165 repoint: function() { 166 var o = this.options, 167 edge; 168 169 if ( o.disabled ) 170 return; 171 172 edge = ( typeof o.position == 'string' ) ? o.position : o.position.edge; 173 174 // Remove arrow classes. 175 this.pointer[0].className = this.pointer[0].className.replace( /wp-pointer-[^\s'"]*/, '' ); 176 177 // Add arrow class. 178 this.pointer.addClass( 'wp-pointer-' + edge ); 179 }, 180 181 _processPosition: function( position ) { 182 var opposite = { 183 top: 'bottom', 184 bottom: 'top', 185 left: 'right', 186 right: 'left' 187 }, 188 result; 189 190 // If the position object is a string, it is shorthand for position.edge. 191 if ( typeof position == 'string' ) { 192 result = { 193 edge: position + '' 194 }; 195 } else { 196 result = $.extend( {}, position ); 197 } 198 199 if ( ! result.edge ) 200 return result; 201 202 if ( result.edge == 'top' || result.edge == 'bottom' ) { 203 result.align = result.align || 'left'; 204 205 result.at = result.at || result.align + ' ' + opposite[ result.edge ]; 206 result.my = result.my || result.align + ' ' + result.edge; 207 } else { 208 result.align = result.align || 'top'; 209 210 result.at = result.at || opposite[ result.edge ] + ' ' + result.align; 211 result.my = result.my || result.edge + ' ' + result.align; 212 } 213 214 return result; 215 }, 216 217 open: function( event ) { 218 var self = this, 219 o = this.options; 220 221 if ( this.active || o.disabled || this.element.is(':hidden') ) 222 return; 223 224 this.update().done( function() { 225 self._open( event ); 226 }); 227 }, 228 229 _open: function( event ) { 230 var self = this, 231 o = this.options; 232 233 if ( this.active || o.disabled || this.element.is(':hidden') ) 234 return; 235 236 this.active = true; 237 238 this._trigger( "open", event, this._handoff() ); 239 240 this._trigger( "show", event, this._handoff({ 241 opened: function() { 242 self._trigger( "opened", event, self._handoff() ); 243 } 244 })); 245 }, 246 247 close: function( event ) { 248 if ( !this.active || this.options.disabled ) 249 return; 250 251 var self = this; 252 this.active = false; 253 254 this._trigger( "close", event, this._handoff() ); 255 this._trigger( "hide", event, this._handoff({ 256 closed: function() { 257 self._trigger( "closed", event, self._handoff() ); 258 } 259 })); 260 }, 261 262 sendToTop: function( event ) { 263 if ( this.active ) 264 this.pointer.css( 'z-index', zindex++ ); 265 }, 266 267 toggle: function( event ) { 268 if ( this.pointer.is(':hidden') ) 269 this.open( event ); 270 else 271 this.close( event ); 272 }, 273 274 _handoff: function( extend ) { 275 return $.extend({ 276 pointer: this.pointer, 277 element: this.element 278 }, extend); 279 } 280 }); 281 })(jQuery);
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
| Generated: Fri May 25 03:56:23 2012 | Hosted by follow the white rabbit. |