|
|
@ -1,6 +1,6 @@ |
|
|
|
// MooTools: the javascript framework.
|
|
|
|
// Load this file's selection again by visiting: http://mootools.net/more/43db227db7a621ebb062ee621432ae3d
|
|
|
|
// Or build this file again with packager using: packager build More/Events.Pseudos More/Date More/Date.Extras More/Element.Forms More/Element.Position More/Element.Shortcuts More/Fx.Scroll More/Fx.Slide More/Sortables More/Request.JSONP More/Request.Periodical
|
|
|
|
// Load this file's selection again by visiting: http://mootools.net/more/7a819726f7f5e85fc48bef295ff78dbe
|
|
|
|
// Or build this file again with packager using: packager build More/Events.Pseudos More/Date More/Date.Extras More/Element.Forms More/Element.Position More/Element.Shortcuts More/Fx.Scroll More/Fx.Slide More/Sortables More/Request.JSONP More/Request.Periodical More/Tips
|
|
|
|
/* |
|
|
|
--- |
|
|
|
|
|
|
@ -3161,3 +3161,264 @@ Request.implement({ |
|
|
|
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
|
|
/* |
|
|
|
--- |
|
|
|
|
|
|
|
script: Tips.js |
|
|
|
|
|
|
|
name: Tips |
|
|
|
|
|
|
|
description: Class for creating nice tips that follow the mouse cursor when hovering an element. |
|
|
|
|
|
|
|
license: MIT-style license |
|
|
|
|
|
|
|
authors: |
|
|
|
- Valerio Proietti |
|
|
|
- Christoph Pojer |
|
|
|
- Luis Merino |
|
|
|
|
|
|
|
requires: |
|
|
|
- Core/Options |
|
|
|
- Core/Events |
|
|
|
- Core/Element.Event |
|
|
|
- Core/Element.Style |
|
|
|
- Core/Element.Dimensions |
|
|
|
- /MooTools.More |
|
|
|
|
|
|
|
provides: [Tips] |
|
|
|
|
|
|
|
... |
|
|
|
*/ |
|
|
|
|
|
|
|
(function(){ |
|
|
|
|
|
|
|
var read = function(option, element){ |
|
|
|
return (option) ? (typeOf(option) == 'function' ? option(element) : element.get(option)) : ''; |
|
|
|
}; |
|
|
|
|
|
|
|
this.Tips = new Class({ |
|
|
|
|
|
|
|
Implements: [Events, Options], |
|
|
|
|
|
|
|
options: {/* |
|
|
|
id: null, |
|
|
|
onAttach: function(element){}, |
|
|
|
onDetach: function(element){}, |
|
|
|
onBound: function(coords){},*/ |
|
|
|
onShow: function(){ |
|
|
|
this.tip.setStyle('display', 'block'); |
|
|
|
}, |
|
|
|
onHide: function(){ |
|
|
|
this.tip.setStyle('display', 'none'); |
|
|
|
}, |
|
|
|
title: 'title', |
|
|
|
text: function(element){ |
|
|
|
return element.get('rel') || element.get('href'); |
|
|
|
}, |
|
|
|
showDelay: 100, |
|
|
|
hideDelay: 100, |
|
|
|
className: 'tip-wrap', |
|
|
|
offset: {x: 16, y: 16}, |
|
|
|
windowPadding: {x:0, y:0}, |
|
|
|
fixed: false, |
|
|
|
waiAria: true |
|
|
|
}, |
|
|
|
|
|
|
|
initialize: function(){ |
|
|
|
var params = Array.link(arguments, { |
|
|
|
options: Type.isObject, |
|
|
|
elements: function(obj){ |
|
|
|
return obj != null; |
|
|
|
} |
|
|
|
}); |
|
|
|
this.setOptions(params.options); |
|
|
|
if (params.elements) this.attach(params.elements); |
|
|
|
this.container = new Element('div', {'class': 'tip'}); |
|
|
|
|
|
|
|
if (this.options.id){ |
|
|
|
this.container.set('id', this.options.id); |
|
|
|
if (this.options.waiAria) this.attachWaiAria(); |
|
|
|
} |
|
|
|
}, |
|
|
|
|
|
|
|
toElement: function(){ |
|
|
|
if (this.tip) return this.tip; |
|
|
|
|
|
|
|
this.tip = new Element('div', { |
|
|
|
'class': this.options.className, |
|
|
|
styles: { |
|
|
|
position: 'absolute', |
|
|
|
top: 0, |
|
|
|
left: 0 |
|
|
|
} |
|
|
|
}).adopt( |
|
|
|
new Element('div', {'class': 'tip-top'}), |
|
|
|
this.container, |
|
|
|
new Element('div', {'class': 'tip-bottom'}) |
|
|
|
); |
|
|
|
|
|
|
|
return this.tip; |
|
|
|
}, |
|
|
|
|
|
|
|
attachWaiAria: function(){ |
|
|
|
var id = this.options.id; |
|
|
|
this.container.set('role', 'tooltip'); |
|
|
|
|
|
|
|
if (!this.waiAria){ |
|
|
|
this.waiAria = { |
|
|
|
show: function(element){ |
|
|
|
if (id) element.set('aria-describedby', id); |
|
|
|
this.container.set('aria-hidden', 'false'); |
|
|
|
}, |
|
|
|
hide: function(element){ |
|
|
|
if (id) element.erase('aria-describedby'); |
|
|
|
this.container.set('aria-hidden', 'true'); |
|
|
|
} |
|
|
|
}; |
|
|
|
} |
|
|
|
this.addEvents(this.waiAria); |
|
|
|
}, |
|
|
|
|
|
|
|
detachWaiAria: function(){ |
|
|
|
if (this.waiAria){ |
|
|
|
this.container.erase('role'); |
|
|
|
this.container.erase('aria-hidden'); |
|
|
|
this.removeEvents(this.waiAria); |
|
|
|
} |
|
|
|
}, |
|
|
|
|
|
|
|
attach: function(elements){ |
|
|
|
$$(elements).each(function(element){ |
|
|
|
var title = read(this.options.title, element), |
|
|
|
text = read(this.options.text, element); |
|
|
|
|
|
|
|
element.set('title', '').store('tip:native', title).retrieve('tip:title', title); |
|
|
|
element.retrieve('tip:text', text); |
|
|
|
this.fireEvent('attach', [element]); |
|
|
|
|
|
|
|
var events = ['enter', 'leave']; |
|
|
|
if (!this.options.fixed) events.push('move'); |
|
|
|
|
|
|
|
events.each(function(value){ |
|
|
|
var event = element.retrieve('tip:' + value); |
|
|
|
if (!event) event = function(event){ |
|
|
|
this['element' + value.capitalize()].apply(this, [event, element]); |
|
|
|
}.bind(this); |
|
|
|
|
|
|
|
element.store('tip:' + value, event).addEvent('mouse' + value, event); |
|
|
|
}, this); |
|
|
|
}, this); |
|
|
|
|
|
|
|
return this; |
|
|
|
}, |
|
|
|
|
|
|
|
detach: function(elements){ |
|
|
|
$$(elements).each(function(element){ |
|
|
|
['enter', 'leave', 'move'].each(function(value){ |
|
|
|
element.removeEvent('mouse' + value, element.retrieve('tip:' + value)).eliminate('tip:' + value); |
|
|
|
}); |
|
|
|
|
|
|
|
this.fireEvent('detach', [element]); |
|
|
|
|
|
|
|
if (this.options.title == 'title'){ // This is necessary to check if we can revert the title
|
|
|
|
var original = element.retrieve('tip:native'); |
|
|
|
if (original) element.set('title', original); |
|
|
|
} |
|
|
|
}, this); |
|
|
|
|
|
|
|
return this; |
|
|
|
}, |
|
|
|
|
|
|
|
elementEnter: function(event, element){ |
|
|
|
clearTimeout(this.timer); |
|
|
|
this.timer = (function(){ |
|
|
|
this.container.empty(); |
|
|
|
|
|
|
|
['title', 'text'].each(function(value){ |
|
|
|
var content = element.retrieve('tip:' + value); |
|
|
|
var div = this['_' + value + 'Element'] = new Element('div', { |
|
|
|
'class': 'tip-' + value |
|
|
|
}).inject(this.container); |
|
|
|
if (content) this.fill(div, content); |
|
|
|
}, this); |
|
|
|
this.show(element); |
|
|
|
this.position((this.options.fixed) ? {page: element.getPosition()} : event); |
|
|
|
}).delay(this.options.showDelay, this); |
|
|
|
}, |
|
|
|
|
|
|
|
elementLeave: function(event, element){ |
|
|
|
clearTimeout(this.timer); |
|
|
|
this.timer = this.hide.delay(this.options.hideDelay, this, element); |
|
|
|
this.fireForParent(event, element); |
|
|
|
}, |
|
|
|
|
|
|
|
setTitle: function(title){ |
|
|
|
if (this._titleElement){ |
|
|
|
this._titleElement.empty(); |
|
|
|
this.fill(this._titleElement, title); |
|
|
|
} |
|
|
|
return this; |
|
|
|
}, |
|
|
|
|
|
|
|
setText: function(text){ |
|
|
|
if (this._textElement){ |
|
|
|
this._textElement.empty(); |
|
|
|
this.fill(this._textElement, text); |
|
|
|
} |
|
|
|
return this; |
|
|
|
}, |
|
|
|
|
|
|
|
fireForParent: function(event, element){ |
|
|
|
element = element.getParent(); |
|
|
|
if (!element || element == document.body) return; |
|
|
|
if (element.retrieve('tip:enter')) element.fireEvent('mouseenter', event); |
|
|
|
else this.fireForParent(event, element); |
|
|
|
}, |
|
|
|
|
|
|
|
elementMove: function(event, element){ |
|
|
|
this.position(event); |
|
|
|
}, |
|
|
|
|
|
|
|
position: function(event){ |
|
|
|
if (!this.tip) document.id(this); |
|
|
|
|
|
|
|
var size = window.getSize(), scroll = window.getScroll(), |
|
|
|
tip = {x: this.tip.offsetWidth, y: this.tip.offsetHeight}, |
|
|
|
props = {x: 'left', y: 'top'}, |
|
|
|
bounds = {y: false, x2: false, y2: false, x: false}, |
|
|
|
obj = {}; |
|
|
|
|
|
|
|
for (var z in props){ |
|
|
|
obj[props[z]] = event.page[z] + this.options.offset[z]; |
|
|
|
if (obj[props[z]] < 0) bounds[z] = true; |
|
|
|
if ((obj[props[z]] + tip[z] - scroll[z]) > size[z] - this.options.windowPadding[z]){ |
|
|
|
obj[props[z]] = event.page[z] - this.options.offset[z] - tip[z]; |
|
|
|
bounds[z+'2'] = true; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
this.fireEvent('bound', bounds); |
|
|
|
this.tip.setStyles(obj); |
|
|
|
}, |
|
|
|
|
|
|
|
fill: function(element, contents){ |
|
|
|
if (typeof contents == 'string') element.set('html', contents); |
|
|
|
else element.adopt(contents); |
|
|
|
}, |
|
|
|
|
|
|
|
show: function(element){ |
|
|
|
if (!this.tip) document.id(this); |
|
|
|
if (!this.tip.getParent()) this.tip.inject(document.body); |
|
|
|
this.fireEvent('show', [this.tip, element]); |
|
|
|
}, |
|
|
|
|
|
|
|
hide: function(element){ |
|
|
|
if (!this.tip) document.id(this); |
|
|
|
this.fireEvent('hide', [this.tip, element]); |
|
|
|
} |
|
|
|
|
|
|
|
}); |
|
|
|
|
|
|
|
})(); |
|
|
|
|
|
|
|