jquery-qtip2-rails 0.3.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/README.md CHANGED
@@ -58,7 +58,7 @@ You can also create your own `app/assets/javascripts/jquery.qtip.js` file:
58
58
  //= include jquery-qtip/src/modal/modal.js
59
59
  //= include jquery-qtip/src/viewport/viewport.js
60
60
  //= include jquery-qtip/src/imagemap/imagemap.js
61
- //= include jquery-qtip/src/bgiframe/bgiframe.js
61
+ //= include jquery-qtip/src/ie6/ie6.js
62
62
  //= include jquery-qtip/src/outro.js
63
63
 
64
64
  And `app/assets/stylesheets/jquery.qtip.css` file:
@@ -69,6 +69,7 @@ And `app/assets/stylesheets/jquery.qtip.css` file:
69
69
  *= include jquery-qtip/src/css3.css
70
70
  *= include jquery-qtip/src/tips/tips.css
71
71
  *= include jquery-qtip/src/modal/modal.css
72
+ *= include jquery-qtip/src/ie6/ie6.css
72
73
  */
73
74
 
74
75
  This allows you to enable only the plugins that you need and thus reduce qTip2 size.
@@ -88,12 +89,14 @@ qTip2 includes a [Twitter Bootstrap theme](http://craigsworks.com/projects/qtip2
88
89
 
89
90
  How to use:
90
91
 
91
- $('.selector').qtip({
92
- content: 'Hello World!'
93
- style: {
94
- classes: 'ui-tooltip-bootstrap'
95
- }
96
- })
92
+ ```JavaScript
93
+ $('.selector').qtip({
94
+ content: 'Hello World!'
95
+ style: {
96
+ classes: 'qtip-bootstrap'
97
+ }
98
+ })
99
+ ```
97
100
 
98
101
  ## License
99
102
 
@@ -1,7 +1,7 @@
1
1
  module Jquery
2
2
  module Qtip2
3
3
  module Rails
4
- VERSION = "0.3.0"
4
+ VERSION = "0.4.0"
5
5
  end
6
6
  end
7
7
  end
@@ -11,15 +11,15 @@ $(document).ready(function() {
11
11
  content: 'no_title'
12
12
  });
13
13
 
14
- $('#ui-tooltip-rounded').qtip({
14
+ $('#qtip-rounded').qtip({
15
15
  position: { target: 'mouse', adjust: { x: 10, y: 10 } },
16
- content: 'ui-tooltip-rounded',
16
+ content: 'qtip-rounded',
17
17
  style: {
18
- classes: 'ui-tooltip-rounded'
18
+ classes: 'qtip-rounded'
19
19
  }
20
20
  });
21
21
 
22
- $('#ui-tooltip-bootstrap').qtip({
22
+ $('#qtip-bootstrap').qtip({
23
23
  position: {
24
24
  my: 'bottom center',
25
25
  at: 'top center',
@@ -29,20 +29,20 @@ $(document).ready(function() {
29
29
  content: {
30
30
  title: {
31
31
  button: 'close',
32
- text: 'ui-tooltip-bootstrap'
32
+ text: 'qtip-bootstrap'
33
33
  },
34
- text: 'ui-tooltip-bootstrap'
34
+ text: 'qtip-bootstrap'
35
35
  },
36
36
  style: {
37
- classes: 'ui-tooltip-bootstrap'
37
+ classes: 'qtip-bootstrap'
38
38
  }
39
39
  });
40
40
 
41
- $('#ui-tooltip-shadow-rounded').qtip({
41
+ $('#qtip-shadow-rounded').qtip({
42
42
  position: { target: 'mouse', adjust: { x: 10, y: 10 } },
43
- content: 'ui-tooltip-shadow ui-tooltip-rounded',
43
+ content: 'qtip-shadow qtip-rounded',
44
44
  style: {
45
- classes: 'ui-tooltip-shadow ui-tooltip-rounded'
45
+ classes: 'qtip-shadow qtip-rounded'
46
46
  }
47
47
  });
48
48
  });
@@ -7,8 +7,8 @@
7
7
 
8
8
  <li><div id="no_title">no_title</div></li>
9
9
 
10
- <li><div id="ui-tooltip-rounded">ui-tooltip-rounded</div></li>
10
+ <li><div id="qtip-rounded">qtip-rounded</div></li>
11
11
 
12
- <li><div id="ui-tooltip-bootstrap">ui-tooltip-bootstrap</div></li>
12
+ <li><div id="qtip-bootstrap">qtip-bootstrap</div></li>
13
13
 
14
- <li><div id="ui-tooltip-shadow-rounded">ui-tooltip-shadow ui-tooltip-rounded</div></li>
14
+ <li><div id="qtip-shadow-rounded">qtip-shadow qtip-rounded</div></li>
@@ -1,103 +1,103 @@
1
1
  /*! Light tooltip style */
2
- .ui-tooltip-light{
2
+ .qtip-light{
3
3
  background-color: white;
4
4
  border-color: #E2E2E2;
5
5
  color: #454545;
6
6
  }
7
7
 
8
- .ui-tooltip-light .ui-tooltip-titlebar{
8
+ .qtip-light .qtip-titlebar{
9
9
  background-color: #f1f1f1;
10
10
  }
11
11
 
12
12
 
13
13
  /*! Dark tooltip style */
14
- .ui-tooltip-dark{
14
+ .qtip-dark{
15
15
  background-color: #505050;
16
16
  border-color: #303030;
17
17
  color: #f3f3f3;
18
18
  }
19
19
 
20
- .ui-tooltip-dark .ui-tooltip-titlebar{
20
+ .qtip-dark .qtip-titlebar{
21
21
  background-color: #404040;
22
22
  }
23
23
 
24
- .ui-tooltip-dark .ui-tooltip-icon{
24
+ .qtip-dark .qtip-icon{
25
25
  border-color: #444;
26
26
  }
27
27
 
28
- .ui-tooltip-dark .ui-tooltip-titlebar .ui-state-hover{
28
+ .qtip-dark .qtip-titlebar .ui-state-hover{
29
29
  border-color: #303030;
30
30
  }
31
31
 
32
32
 
33
33
  /*! Cream tooltip style */
34
- .ui-tooltip-cream{
34
+ .qtip-cream{
35
35
  background-color: #FBF7AA;
36
36
  border-color: #F9E98E;
37
37
  color: #A27D35;
38
38
  }
39
39
 
40
- .ui-tooltip-cream .ui-tooltip-titlebar{
40
+ .qtip-cream .qtip-titlebar{
41
41
  background-color: #F0DE7D;
42
42
  }
43
43
 
44
- .ui-tooltip-cream .ui-state-default .ui-tooltip-icon{
44
+ .qtip-cream .qtip-close .qtip-icon{
45
45
  background-position: -82px 0;
46
46
  }
47
47
 
48
48
 
49
49
  /*! Red tooltip style */
50
- .ui-tooltip-red{
50
+ .qtip-red{
51
51
  background-color: #F78B83;
52
52
  border-color: #D95252;
53
53
  color: #912323;
54
54
  }
55
55
 
56
- .ui-tooltip-red .ui-tooltip-titlebar{
56
+ .qtip-red .qtip-titlebar{
57
57
  background-color: #F06D65;
58
58
  }
59
59
 
60
- .ui-tooltip-red .ui-state-default .ui-tooltip-icon{
60
+ .qtip-red .qtip-close .qtip-icon{
61
61
  background-position: -102px 0;
62
62
  }
63
63
 
64
- .ui-tooltip-red .ui-tooltip-icon{
64
+ .qtip-red .qtip-icon{
65
65
  border-color: #D95252;
66
66
  }
67
67
 
68
- .ui-tooltip-red .ui-tooltip-titlebar .ui-state-hover{
68
+ .qtip-red .qtip-titlebar .ui-state-hover{
69
69
  border-color: #D95252;
70
70
  }
71
71
 
72
72
 
73
73
  /*! Green tooltip style */
74
- .ui-tooltip-green{
74
+ .qtip-green{
75
75
  background-color: #CAED9E;
76
76
  border-color: #90D93F;
77
77
  color: #3F6219;
78
78
  }
79
79
 
80
- .ui-tooltip-green .ui-tooltip-titlebar{
80
+ .qtip-green .qtip-titlebar{
81
81
  background-color: #B0DE78;
82
82
  }
83
83
 
84
- .ui-tooltip-green .ui-state-default .ui-tooltip-icon{
84
+ .qtip-green .qtip-close .qtip-icon{
85
85
  background-position: -42px 0;
86
86
  }
87
87
 
88
88
 
89
89
  /*! Blue tooltip style */
90
- .ui-tooltip-blue{
90
+ .qtip-blue{
91
91
  background-color: #E5F6FE;
92
92
  border-color: #ADD9ED;
93
93
  color: #5E99BD;
94
94
  }
95
95
 
96
- .ui-tooltip-blue .ui-tooltip-titlebar{
96
+ .qtip-blue .qtip-titlebar{
97
97
  background-color: #D0E9F5;
98
98
  }
99
99
 
100
- .ui-tooltip-blue .ui-state-default .ui-tooltip-icon{
100
+ .qtip-blue .qtip-close .qtip-icon{
101
101
  background-position: -2px 0;
102
102
  }
103
103
 
@@ -1,22 +1,5 @@
1
- /* Fluid class for determining actual width in IE */
2
- #qtip-rcontainer{
3
- position: absolute;
4
- left: -28000px;
5
- top: -28000px;
6
- display: block;
7
- visibility: hidden;
8
- }
9
-
10
- /* Fluid class for determining actual width in IE */
11
- #qtip-rcontainer .ui-tooltip{
12
- display: block !important;
13
- visibility: hidden !important;
14
- position: static !important;
15
- float: left !important;
16
- }
17
-
18
1
  /* Core qTip styles */
19
- .ui-tooltip, .qtip{
2
+ .qtip, .qtip{
20
3
  position: absolute;
21
4
  left: -28000px;
22
5
  top: -28000px;
@@ -27,9 +10,11 @@
27
10
 
28
11
  font-size: 10.5px;
29
12
  line-height: 12px;
13
+
14
+ direction: ltr;
30
15
  }
31
16
 
32
- .ui-tooltip-content{
17
+ .qtip-content{
33
18
  position: relative;
34
19
  padding: 5px 9px;
35
20
  overflow: hidden;
@@ -38,9 +23,8 @@
38
23
  word-wrap: break-word;
39
24
  }
40
25
 
41
- .ui-tooltip-titlebar{
26
+ .qtip-titlebar{
42
27
  position: relative;
43
- min-height: 14px;
44
28
  padding: 5px 35px 5px 10px;
45
29
  overflow: hidden;
46
30
 
@@ -48,39 +32,44 @@
48
32
  font-weight: bold;
49
33
  }
50
34
 
51
- .ui-tooltip-titlebar + .ui-tooltip-content{ border-top-width: 0 !important; }
35
+ .qtip-titlebar + .qtip-content{ border-top-width: 0 !important; }
52
36
 
53
- /* Default close button class */
54
- .ui-tooltip-titlebar .ui-state-default{
55
- position: absolute;
56
- right: 4px;
57
- top: 50%;
58
- margin-top: -9px;
37
+ /* Default close button class */
38
+ .qtip-close{
39
+ position: absolute;
40
+ right: -9px; top: -9px;
41
+
42
+ cursor: pointer;
43
+ outline: medium none;
59
44
 
60
- cursor: pointer;
61
- outline: medium none;
45
+ border-width: 1px;
46
+ border-style: solid;
47
+ border-color: transparent;
48
+ }
62
49
 
63
- border-width: 1px;
64
- border-style: solid;
50
+ .qtip-titlebar .qtip-close{
51
+ right: 4px; top: 50%;
52
+ margin-top: -9px;
65
53
  }
66
-
67
- * html .ui-tooltip-titlebar .ui-state-default{ top: 16px; } /* IE fix */
54
+
55
+ * html .qtip-titlebar .qtip-close{ top: 16px; } /* IE fix */
68
56
 
69
- .ui-tooltip-titlebar .ui-icon,
70
- .ui-tooltip-icon .ui-icon{
57
+ .qtip-titlebar .ui-icon,
58
+ .qtip-icon .ui-icon{
71
59
  display: block;
72
60
  text-indent: -1000em;
73
61
  direction: ltr;
62
+ vertical-align: middle;
74
63
  }
75
64
 
76
- .ui-tooltip-icon, .ui-tooltip-icon .ui-icon{
65
+ .qtip-icon, .qtip-icon .ui-icon{
77
66
  -moz-border-radius: 3px;
78
67
  -webkit-border-radius: 3px;
79
68
  border-radius: 3px;
80
69
  text-decoration: none;
81
70
  }
82
71
 
83
- .ui-tooltip-icon .ui-icon{
72
+ .qtip-icon .ui-icon{
84
73
  width: 18px;
85
74
  height: 14px;
86
75
 
@@ -94,13 +83,13 @@
94
83
 
95
84
 
96
85
  /* Applied to 'focused' tooltips e.g. most recently displayed/interacted with */
97
- .ui-tooltip-focus{}
86
+ .qtip-focus{}
98
87
 
99
88
  /* Applied on hover of tooltips i.e. added/removed on mouseenter/mouseleave respectively */
100
- .ui-tooltip-hover{}
89
+ .qtip-hover{}
101
90
 
102
91
  /* Default tooltip style */
103
- .ui-tooltip-default{
92
+ .qtip-default{
104
93
  border-width: 1px;
105
94
  border-style: solid;
106
95
  border-color: #F1D031;
@@ -109,17 +98,17 @@
109
98
  color: #555;
110
99
  }
111
100
 
112
- .ui-tooltip-default .ui-tooltip-titlebar{
101
+ .qtip-default .qtip-titlebar{
113
102
  background-color: #FFEF93;
114
103
  }
115
104
 
116
- .ui-tooltip-default .ui-tooltip-icon{
105
+ .qtip-default .qtip-icon{
117
106
  border-color: #CCC;
118
107
  background: #F1F1F1;
119
108
  color: #777;
120
109
  }
121
110
 
122
- .ui-tooltip-default .ui-tooltip-titlebar .ui-state-hover{
111
+ .qtip-default .qtip-titlebar .qtip-close{
123
112
  border-color: #AAA;
124
113
  color: #111;
125
114
  }
@@ -2,7 +2,7 @@
2
2
  function sanitizeOptions(opts)
3
3
  {
4
4
  var invalid = function(a) { return a === NULL || 'object' !== typeof a; },
5
- invalidContent = function(c) { return !$.isFunction(c) && ((!c && !c.attr) || c.length < 1 || ('object' === typeof c && !c.jquery)); };
5
+ invalidContent = function(c) { return !$.isFunction(c) && ((!c && !c.attr) || c.length < 1 || ('object' === typeof c && !c.jquery && !c.then)); };
6
6
 
7
7
  if(!opts || 'object' !== typeof opts) { return FALSE; }
8
8
 
@@ -62,11 +62,12 @@ function QTip(target, options, id, attr)
62
62
  // Declare this reference
63
63
  var self = this,
64
64
  docBody = document.body,
65
- tooltipID = uitooltip + '-' + id,
65
+ tooltipID = NAMESPACE + '-' + id,
66
66
  isPositioning = 0,
67
67
  isDrawing = 0,
68
68
  tooltip = $(),
69
69
  namespace = '.qtip-' + id,
70
+ disabledClass = 'qtip-disabled',
70
71
  elements, cache;
71
72
 
72
73
  // Setup class attributes
@@ -87,9 +88,6 @@ function QTip(target, options, id, attr)
87
88
  lastClass: ''
88
89
  };
89
90
 
90
- /*
91
- * Private core functions
92
- */
93
91
  function convertNotation(notation)
94
92
  {
95
93
  var i = 0, obj, option = options,
@@ -105,29 +103,30 @@ function QTip(target, options, id, attr)
105
103
  return [obj || options, levels.pop()];
106
104
  }
107
105
 
108
- function triggerEvent(type, args, event) {
109
- var callback = $.Event('tooltip'+type);
110
- callback.originalEvent = (event ? $.extend({}, event) : NULL) || cache.event || NULL;
111
- tooltip.trigger(callback, [self].concat(args || []));
112
-
113
- return !callback.isDefaultPrevented();
106
+ function createWidgetClass(cls)
107
+ {
108
+ return widget.concat('').join(cls ? '-'+cls+' ' : ' ');
114
109
  }
115
110
 
116
111
  function setWidget()
117
112
  {
118
- var on = options.style.widget;
113
+ var on = options.style.widget,
114
+ disabled = tooltip.hasClass(disabledClass);
119
115
 
120
- tooltip.toggleClass('ui-helper-reset '+widget, on).toggleClass(defaultClass, options.style.def && !on);
116
+ tooltip.removeClass(disabledClass);
117
+ disabledClass = on ? 'ui-state-disabled' : 'qtip-disabled';
118
+ tooltip.toggleClass(disabledClass, disabled);
121
119
 
120
+ tooltip.toggleClass('ui-helper-reset '+createWidgetClass(), on).toggleClass(defaultClass, options.style.def && !on);
121
+
122
122
  if(elements.content) {
123
- elements.content.toggleClass(widget+'-content', on);
123
+ elements.content.toggleClass( createWidgetClass('content'), on);
124
124
  }
125
-
126
125
  if(elements.titlebar) {
127
- elements.titlebar.toggleClass(widget+'-header', on);
126
+ elements.titlebar.toggleClass( createWidgetClass('header'), on);
128
127
  }
129
128
  if(elements.button) {
130
- elements.button.toggleClass(uitooltip+'-icon', !on);
129
+ elements.button.toggleClass(NAMESPACE+'-icon', !on);
131
130
  }
132
131
  }
133
132
 
@@ -156,7 +155,7 @@ function QTip(target, options, id, attr)
156
155
  }
157
156
  else {
158
157
  elements.button = $('<a />', {
159
- 'class': 'ui-state-default ui-tooltip-close ' + (options.style.widget ? '' : uitooltip+'-icon'),
158
+ 'class': 'qtip-close ' + (options.style.widget ? '' : NAMESPACE+'-icon'),
160
159
  'title': close,
161
160
  'aria-label': close
162
161
  })
@@ -169,15 +168,12 @@ function QTip(target, options, id, attr)
169
168
  }
170
169
 
171
170
  // Create button and setup attributes
172
- elements.button.appendTo(elements.titlebar)
171
+ elements.button.appendTo(elements.titlebar || tooltip)
173
172
  .attr('role', 'button')
174
173
  .click(function(event) {
175
- if(!tooltip.hasClass(disabled)) { self.hide(event); }
174
+ if(!tooltip.hasClass(disabledClass)) { self.hide(event); }
176
175
  return FALSE;
177
176
  });
178
-
179
- // Redraw the tooltip when we're done
180
- self.redraw();
181
177
  }
182
178
 
183
179
  function createTitle()
@@ -189,36 +185,32 @@ function QTip(target, options, id, attr)
189
185
 
190
186
  // Create title bar and title elements
191
187
  elements.titlebar = $('<div />', {
192
- 'class': uitooltip + '-titlebar ' + (options.style.widget ? 'ui-widget-header' : '')
188
+ 'class': NAMESPACE + '-titlebar ' + (options.style.widget ? createWidgetClass('header') : '')
193
189
  })
194
190
  .append(
195
191
  elements.title = $('<div />', {
196
192
  'id': id,
197
- 'class': uitooltip + '-title',
193
+ 'class': NAMESPACE + '-title',
198
194
  'aria-atomic': TRUE
199
195
  })
200
196
  )
201
197
  .insertBefore(elements.content)
202
198
 
203
199
  // Button-specific events
204
- .delegate('.ui-tooltip-close', 'mousedown keydown mouseup keyup mouseout', function(event) {
200
+ .delegate('.qtip-close', 'mousedown keydown mouseup keyup mouseout', function(event) {
205
201
  $(this).toggleClass('ui-state-active ui-state-focus', event.type.substr(-4) === 'down');
206
202
  })
207
- .delegate('.ui-tooltip-close', 'mouseover mouseout', function(event){
203
+ .delegate('.qtip-close', 'mouseover mouseout', function(event){
208
204
  $(this).toggleClass('ui-state-hover', event.type === 'mouseover');
209
205
  });
210
206
 
211
207
  // Create button if enabled
212
208
  if(options.content.title.button) { createButton(); }
213
-
214
- // Redraw the tooltip dimensions if it's rendered
215
- else if(self.rendered){ self.redraw(); }
216
209
  }
217
210
 
218
211
  function updateButton(button)
219
212
  {
220
- var elem = elements.button,
221
- title = elements.title;
213
+ var elem = elements.button;
222
214
 
223
215
  // Make sure tooltip is rendered and if not, return
224
216
  if(!self.rendered) { return FALSE; }
@@ -227,9 +219,6 @@ function QTip(target, options, id, attr)
227
219
  elem.remove();
228
220
  }
229
221
  else {
230
- if(!title) {
231
- createTitle();
232
- }
233
222
  createButton();
234
223
  }
235
224
  }
@@ -257,14 +246,22 @@ function QTip(target, options, id, attr)
257
246
  // Content is a regular string, insert the new content
258
247
  else { elem.html(content); }
259
248
 
260
- // Redraw and reposition
261
- self.redraw();
249
+ // Reposition if rnedered
262
250
  if(reposition !== FALSE && self.rendered && tooltip[0].offsetWidth > 0) {
263
251
  self.reposition(cache.event);
264
252
  }
265
253
  }
266
254
 
267
- function updateContent(content, reposition)
255
+ function deferredContent(deferred)
256
+ {
257
+ if(deferred && $.isFunction(deferred.done)) {
258
+ deferred.done(function(c) {
259
+ updateContent(c, null, FALSE);
260
+ });
261
+ }
262
+ }
263
+
264
+ function updateContent(content, reposition, checkDeferred)
268
265
  {
269
266
  var elem = elements.content;
270
267
 
@@ -276,6 +273,11 @@ function QTip(target, options, id, attr)
276
273
  content = content.call(target, cache.event, self) || '';
277
274
  }
278
275
 
276
+ // Handle deferred content
277
+ if(checkDeferred !== FALSE) {
278
+ deferredContent(options.content.deferred);
279
+ }
280
+
279
281
  // Append new content if its a DOM array and show it if hidden
280
282
  if(content.jquery && content.length > 0) {
281
283
  elem.empty().append(content.css({ display: 'block' }));
@@ -298,7 +300,6 @@ function QTip(target, options, id, attr)
298
300
 
299
301
  // If queue is empty after image removal, update tooltip and continue the queue
300
302
  if($.isEmptyObject(srcs)) {
301
- self.redraw();
302
303
  if(reposition !== FALSE) {
303
304
  self.reposition(cache.event);
304
305
  }
@@ -370,7 +371,7 @@ function QTip(target, options, id, attr)
370
371
  // Define show event method
371
372
  function showMethod(event)
372
373
  {
373
- if(tooltip.hasClass(disabled)) { return FALSE; }
374
+ if(tooltip.hasClass(disabledClass)) { return FALSE; }
374
375
 
375
376
  // Clear hide timers
376
377
  clearTimeout(self.timers.show);
@@ -387,7 +388,7 @@ function QTip(target, options, id, attr)
387
388
  // Define hide method
388
389
  function hideMethod(event)
389
390
  {
390
- if(tooltip.hasClass(disabled) || isPositioning || isDrawing) { return FALSE; }
391
+ if(tooltip.hasClass(disabledClass) || isPositioning || isDrawing) { return FALSE; }
391
392
 
392
393
  // Check if new target was actually the tooltip element
393
394
  var relatedTarget = $(event.relatedTarget || event.target),
@@ -413,7 +414,7 @@ function QTip(target, options, id, attr)
413
414
  // Define inactive method
414
415
  function inactiveMethod(event)
415
416
  {
416
- if(tooltip.hasClass(disabled)) { return FALSE; }
417
+ if(tooltip.hasClass(disabledClass)) { return FALSE; }
417
418
 
418
419
  // Clear timer
419
420
  clearTimeout(self.timers.inactive);
@@ -452,7 +453,7 @@ function QTip(target, options, id, attr)
452
453
 
453
454
  // Clear hide timer on tooltip hover to prevent it from closing
454
455
  tooltip.bind('mouseover'+namespace, function() {
455
- if(!tooltip.hasClass(disabled)) { clearTimeout(self.timers.hide); }
456
+ if(!tooltip.hasClass(disabledClass)) { clearTimeout(self.timers.hide); }
456
457
  });
457
458
  }
458
459
 
@@ -468,9 +469,9 @@ function QTip(target, options, id, attr)
468
469
 
469
470
  // Hide tooltip on document mousedown if unfocus events are enabled
470
471
  if(('' + options.hide.event).indexOf('unfocus') > -1) {
471
- posOptions.container.closest('html').bind('mousedown'+namespace, function(event) {
472
+ posOptions.container.closest('html').bind('mousedown'+namespace+' touchstart'+namespace, function(event) {
472
473
  var elem = $(event.target),
473
- enabled = self.rendered && !tooltip.hasClass(disabled) && tooltip[0].offsetWidth > 0,
474
+ enabled = self.rendered && !tooltip.hasClass(disabledClass) && tooltip[0].offsetWidth > 0,
474
475
  isAncestor = elem.parents(selector).filter(tooltip[0]).length > 0;
475
476
 
476
477
  if(elem[0] !== target[0] && elem[0] !== tooltip[0] && !isAncestor &&
@@ -536,9 +537,7 @@ function QTip(target, options, id, attr)
536
537
  // Mouse positioning events
537
538
  if(posOptions.target === 'mouse') {
538
539
  // Cache mousemove coords on show targets
539
- targets.show.bind('mousemove'+namespace, function(event) {
540
- MOUSE = { pageX: event.pageX, pageY: event.pageY, type: 'mousemove' };
541
- });
540
+ targets.show.bind('mousemove'+namespace, storeMouse);
542
541
 
543
542
  // If mouse adjustment is on...
544
543
  if(posOptions.adjust.mouse) {
@@ -558,7 +557,7 @@ function QTip(target, options, id, attr)
558
557
  // Update tooltip position on mousemove
559
558
  targets.document.bind('mousemove'+namespace, function(event) {
560
559
  // Update the tooltip position only if the tooltip is visible and adjustment is enabled
561
- if(self.rendered && cache.onTarget && !tooltip.hasClass(disabled) && tooltip[0].offsetWidth > 0) {
560
+ if(self.rendered && cache.onTarget && !tooltip.hasClass(disabledClass) && tooltip[0].offsetWidth > 0) {
562
561
  self.reposition(event || MOUSE);
563
562
  }
564
563
  });
@@ -570,10 +569,8 @@ function QTip(target, options, id, attr)
570
569
  ($.event.special.resize ? targets.viewport : targets.window).bind('resize'+namespace, repositionMethod);
571
570
  }
572
571
 
573
- // Adjust tooltip position on scroll if screen adjustment is enabled
574
- if(targets.viewport.length || (IE6 && tooltip.css('position') === 'fixed')) {
575
- targets.viewport.bind('scroll'+namespace, repositionMethod);
576
- }
572
+ // Adjust tooltip position on scroll of the window or viewport element if present
573
+ targets.window.add(posOptions.container).bind('scroll'+namespace, repositionMethod);
577
574
  }
578
575
 
579
576
  function unassignEvents()
@@ -603,7 +600,7 @@ function QTip(target, options, id, attr)
603
600
  // Core checks
604
601
  '^id$': function(obj, o, v) {
605
602
  var id = v === TRUE ? QTIP.nextid : v,
606
- tooltipID = uitooltip + '-' + id;
603
+ tooltipID = NAMESPACE + '-' + id;
607
604
 
608
605
  if(id !== FALSE && id.length > 0 && !$('#'+tooltipID).length) {
609
606
  tooltip[0].id = tooltipID;
@@ -613,7 +610,8 @@ function QTip(target, options, id, attr)
613
610
  },
614
611
 
615
612
  // Content checks
616
- '^content.text$': function(obj, o, v){ updateContent(v); },
613
+ '^content.text$': function(obj, o, v) { updateContent(options.content.text); },
614
+ '^content.deferred$': function(obj, o, v) { deferredContent(options.content.deferred); },
617
615
  '^content.title.text$': function(obj, o, v) {
618
616
  // Remove title if content is null
619
617
  if(!v) { return removeTitle(); }
@@ -643,7 +641,10 @@ function QTip(target, options, id, attr)
643
641
 
644
642
  // Style checks
645
643
  '^style.classes$': function(obj, o, v) {
646
- tooltip.attr('class', uitooltip + ' qtip ' + v);
644
+ tooltip.attr('class', NAMESPACE + ' qtip ' + v);
645
+ },
646
+ '^style.width|height': function(obj, o, v) {
647
+ tooltip.css(o, v);
647
648
  },
648
649
  '^style.widget|content.title': setWidget,
649
650
 
@@ -664,16 +665,28 @@ function QTip(target, options, id, attr)
664
665
  }
665
666
  };
666
667
 
667
- /*
668
- * Public API methods
669
- */
670
668
  $.extend(self, {
669
+ /*
670
+ * Psuedo-private API methods
671
+ */
672
+ _triggerEvent: function(type, args, event)
673
+ {
674
+ var callback = $.Event('tooltip'+type);
675
+ callback.originalEvent = (event ? $.extend({}, event) : NULL) || cache.event || NULL;
676
+ tooltip.trigger(callback, [self].concat(args || []));
677
+
678
+ return !callback.isDefaultPrevented();
679
+ },
680
+
681
+ /*
682
+ * Public API methods
683
+ */
671
684
  render: function(show)
672
685
  {
673
686
  if(self.rendered) { return self; } // If tooltip has already been rendered, exit
674
687
 
675
688
  var text = options.content.text,
676
- title = options.content.title.text,
689
+ title = options.content.title,
677
690
  posOptions = options.position;
678
691
 
679
692
  // Add ARIA attributes to target
@@ -682,7 +695,7 @@ function QTip(target, options, id, attr)
682
695
  // Create tooltip element
683
696
  tooltip = elements.tooltip = $('<div/>', {
684
697
  'id': tooltipID,
685
- 'class': uitooltip + ' qtip ' + defaultClass + ' ' + options.style.classes + ' '+ uitooltip + '-pos-' + options.position.my.abbrev(),
698
+ 'class': [ NAMESPACE, defaultClass, options.style.classes, NAMESPACE + '-pos-' + options.position.my.abbrev() ].join(' '),
686
699
  'width': options.style.width || '',
687
700
  'height': options.style.height || '',
688
701
  'tracking': posOptions.target === 'mouse' && posOptions.adjust.mouse,
@@ -694,32 +707,35 @@ function QTip(target, options, id, attr)
694
707
  'aria-describedby': tooltipID + '-content',
695
708
  'aria-hidden': TRUE
696
709
  })
697
- .toggleClass(disabled, cache.disabled)
710
+ .toggleClass(disabledClass, cache.disabled)
698
711
  .data('qtip', self)
699
712
  .appendTo(options.position.container)
700
713
  .append(
701
714
  // Create content element
702
715
  elements.content = $('<div />', {
703
- 'class': uitooltip + '-content',
716
+ 'class': NAMESPACE + '-content',
704
717
  'id': tooltipID + '-content',
705
718
  'aria-atomic': TRUE
706
719
  })
707
720
  );
708
721
 
709
- // Set rendered flag and prevent redundant redraw/reposition calls for now
722
+ // Set rendered flag and prevent redundant reposition calls for now
710
723
  self.rendered = -1;
711
- isDrawing = 1; isPositioning = 1;
724
+ isPositioning = 1;
712
725
 
713
726
  // Create title...
714
- if(title) {
727
+ if(title.text) {
715
728
  createTitle();
716
729
 
717
730
  // Update title only if its not a callback (called in toggle if so)
718
- if(!$.isFunction(title)) { updateTitle(title, FALSE); }
731
+ if(!$.isFunction(title.text)) { updateTitle(title.text, FALSE); }
719
732
  }
720
733
 
734
+ // Create button
735
+ else if(title.button) { createButton(); }
736
+
721
737
  // Set proper rendered flag and update content if not a callback function (called in toggle)
722
- if(!$.isFunction(text)) { updateContent(text, FALSE); }
738
+ if(!$.isFunction(text) || text.then) { updateContent(text, FALSE); }
723
739
  self.rendered = TRUE;
724
740
 
725
741
  // Setup widget classes
@@ -747,13 +763,10 @@ function QTip(target, options, id, attr)
747
763
  */
748
764
  tooltip.queue('fx', function(next) {
749
765
  // tooltiprender event
750
- triggerEvent('render');
766
+ self._triggerEvent('render');
751
767
 
752
768
  // Reset flags
753
- isDrawing = 0; isPositioning = 0;
754
-
755
- // Redraw the tooltip manually now we're fully rendered
756
- self.redraw();
769
+ isPositioning = 0;
757
770
 
758
771
  // Show tooltip if needed
759
772
  if(options.show.ready || show) {
@@ -774,7 +787,8 @@ function QTip(target, options, id, attr)
774
787
  {
775
788
  case 'dimensions':
776
789
  result = {
777
- height: tooltip.outerHeight(), width: tooltip.outerWidth()
790
+ height: tooltip.outerHeight(FALSE),
791
+ width: tooltip.outerWidth(FALSE)
778
792
  };
779
793
  break;
780
794
 
@@ -797,7 +811,6 @@ function QTip(target, options, id, attr)
797
811
  var rmove = /^position\.(my|at|adjust|target|container)|style|content|show\.ready/i,
798
812
  rdraw = /^content\.(title|attr)|style/i,
799
813
  reposition = FALSE,
800
- redraw = FALSE,
801
814
  checks = self.checks,
802
815
  name;
803
816
 
@@ -831,9 +844,8 @@ function QTip(target, options, id, attr)
831
844
  // Set the new params for the callback
832
845
  option[notation] = [obj[0], obj[1], value, previous];
833
846
 
834
- // Also check if we need to reposition / redraw
847
+ // Also check if we need to reposition
835
848
  reposition = rmove.test(notation) || reposition;
836
- redraw = rdraw.test(notation) || redraw;
837
849
  });
838
850
 
839
851
  // Re-sanitize options
@@ -841,17 +853,13 @@ function QTip(target, options, id, attr)
841
853
 
842
854
  /*
843
855
  * Execute any valid callbacks for the set options
844
- * Also set isPositioning/isDrawing so we don't get loads of redundant repositioning
845
- * and redraw calls.
856
+ * Also set isPositioning/isDrawing so we don't get loads of redundant repositioning calls.
846
857
  */
847
- isPositioning = isDrawing = 1; $.each(option, callback); isPositioning = isDrawing = 0;
858
+ isPositioning = 1; $.each(option, callback); isPositioning = 0;
848
859
 
849
- // Update position / redraw if needed
850
- if(self.rendered && tooltip[0].offsetWidth > 0) {
851
- if(reposition) {
852
- self.reposition( options.position.target === 'mouse' ? NULL : cache.event );
853
- }
854
- if(redraw) { self.redraw(); }
860
+ // Update position if needed
861
+ if(self.rendered && tooltip[0].offsetWidth > 0 && reposition) {
862
+ self.reposition( options.position.target === 'mouse' ? NULL : cache.event );
855
863
  }
856
864
 
857
865
  return self;
@@ -859,6 +867,18 @@ function QTip(target, options, id, attr)
859
867
 
860
868
  toggle: function(state, event)
861
869
  {
870
+ // Try to prevent flickering when tooltip overlaps show element
871
+ if(event) {
872
+ if((/over|enter/).test(event.type) && (/out|leave/).test(cache.event.type) &&
873
+ options.show.target.add(event.target).length === options.show.target.length &&
874
+ tooltip.has(event.relatedTarget).length) {
875
+ return self;
876
+ }
877
+
878
+ // Cache event
879
+ cache.event = $.extend({}, event);
880
+ }
881
+
862
882
  // Render the tooltip if showing and it isn't already
863
883
  if(!self.rendered) { return state ? self.render(1) : self; }
864
884
 
@@ -878,20 +898,8 @@ function QTip(target, options, id, attr)
878
898
  // Return if element is already in correct state
879
899
  if(!tooltip.is(':animated') && visible === state && sameTarget) { return self; }
880
900
 
881
- // Try to prevent flickering when tooltip overlaps show element
882
- if(event) {
883
- if((/over|enter/).test(event.type) && (/out|leave/).test(cache.event.type) &&
884
- options.show.target.add(event.target).length === options.show.target.length &&
885
- tooltip.has(event.relatedTarget).length) {
886
- return self;
887
- }
888
-
889
- // Cache event
890
- cache.event = $.extend({}, event);
891
- }
892
-
893
901
  // tooltipshow/tooltiphide events
894
- if(!triggerEvent(type, [90])) { return self; }
902
+ if(!self._triggerEvent(type, [90])) { return self; }
895
903
 
896
904
  // Set ARIA hidden status attribute
897
905
  $.attr(tooltip[0], 'aria-hidden', !!!state);
@@ -910,9 +918,7 @@ function QTip(target, options, id, attr)
910
918
 
911
919
  // Cache mousemove events for positioning purposes (if not already tracking)
912
920
  if(!trackingBound && posOptions.target === 'mouse' && posOptions.adjust.mouse) {
913
- $(document).bind('mousemove.qtip', function(event) {
914
- MOUSE = { pageX: event.pageX, pageY: event.pageY, type: 'mousemove' };
915
- });
921
+ $(document).bind('mousemove.qtip', storeMouse);
916
922
  trackingBound = TRUE;
917
923
  }
918
924
 
@@ -921,7 +927,8 @@ function QTip(target, options, id, attr)
921
927
 
922
928
  // Hide other tooltips if tooltip is solo
923
929
  if(!!opts.solo) {
924
- $(selector, opts.solo).not(tooltip).qtip('hide', $.Event('tooltipsolo'));
930
+ (typeof opts.solo === 'string' ? $(opts.solo) : $(selector, opts.solo))
931
+ .not(tooltip).not(opts.target).qtip('hide', $.Event('tooltipsolo'));
925
932
  }
926
933
  }
927
934
  else {
@@ -970,7 +977,7 @@ function QTip(target, options, id, attr)
970
977
  }
971
978
 
972
979
  // tooltipvisible/tooltiphidden events
973
- triggerEvent(state ? 'visible' : 'hidden');
980
+ self._triggerEvent(state ? 'visible' : 'hidden');
974
981
  }
975
982
 
976
983
  // If no effect type is supplied, use a simple toggle
@@ -1013,7 +1020,7 @@ function QTip(target, options, id, attr)
1013
1020
  if(!tooltip.hasClass(focusClass))
1014
1021
  {
1015
1022
  // tooltipfocus event
1016
- if(triggerEvent('focus', [newIndex], cachedEvent)) {
1023
+ if(self._triggerEvent('focus', [newIndex], cachedEvent)) {
1017
1024
  // Only update z-index's if they've changed
1018
1025
  if(curIndex !== newIndex) {
1019
1026
  // Reduce our z-index's and keep them properly ordered
@@ -1040,7 +1047,7 @@ function QTip(target, options, id, attr)
1040
1047
  tooltip.removeClass(focusClass);
1041
1048
 
1042
1049
  // tooltipblur event
1043
- triggerEvent('blur', [tooltip.css('zIndex')], event);
1050
+ self._triggerEvent('blur', [tooltip.css('zIndex')], event);
1044
1051
 
1045
1052
  return self;
1046
1053
  },
@@ -1058,16 +1065,18 @@ function QTip(target, options, id, attr)
1058
1065
  at = posOptions.at,
1059
1066
  adjust = posOptions.adjust,
1060
1067
  method = adjust.method.split(' '),
1061
- elemWidth = tooltip.outerWidth(),
1062
- elemHeight = tooltip.outerHeight(),
1068
+ elemWidth = tooltip.outerWidth(FALSE),
1069
+ elemHeight = tooltip.outerHeight(FALSE),
1063
1070
  targetWidth = 0,
1064
1071
  targetHeight = 0,
1065
- fixed = tooltip.css('position') === 'fixed',
1072
+ type = tooltip.css('position'),
1066
1073
  viewport = posOptions.viewport,
1067
1074
  position = { left: 0, top: 0 },
1068
1075
  container = posOptions.container,
1069
1076
  visible = tooltip[0].offsetWidth > 0,
1070
- adjusted, offset, win;
1077
+ isScroll = event && event.type === 'scroll',
1078
+ win = $(window),
1079
+ adjusted, offset;
1071
1080
 
1072
1081
  // Check if absolute position was passed
1073
1082
  if($.isArray(target) && target.length === 2) {
@@ -1082,14 +1091,21 @@ function QTip(target, options, id, attr)
1082
1091
  at = { x: LEFT, y: TOP };
1083
1092
 
1084
1093
  // Use cached event if one isn't available for positioning
1085
- event = (event && (event.type === 'resize' || event.type === 'scroll') ? cache.event :
1094
+ event = MOUSE && MOUSE.pageX && (adjust.mouse || !event || !event.pageX) ? { pageX: MOUSE.pageX, pageY: MOUSE.pageY } :
1095
+ (event && (event.type === 'resize' || event.type === 'scroll') ? cache.event :
1086
1096
  event && event.pageX && event.type === 'mousemove' ? event :
1087
- MOUSE && MOUSE.pageX && (adjust.mouse || !event || !event.pageX) ? { pageX: MOUSE.pageX, pageY: MOUSE.pageY } :
1088
- !adjust.mouse && cache.origin && cache.origin.pageX && options.show.distance ? cache.origin :
1097
+ (!adjust.mouse || options.show.distance) && cache.origin && cache.origin.pageX ? cache.origin :
1089
1098
  event) || event || cache.event || MOUSE || {};
1090
1099
 
1091
1100
  // Use event coordinates for position
1092
- position = { top: event.pageY, left: event.pageX };
1101
+ if(type !== 'static') { position = container.offset(); }
1102
+ position = { left: event.pageX - position.left, top: event.pageY - position.top };
1103
+
1104
+ // Scroll events are a pain, some browsers
1105
+ if(adjust.mouse && isScroll) {
1106
+ position.left -= MOUSE.scrollX - win.scrollLeft();
1107
+ position.top -= MOUSE.scrollY - win.scrollTop();
1108
+ }
1093
1109
  }
1094
1110
 
1095
1111
  // Target wasn't mouse or absolute...
@@ -1124,13 +1140,13 @@ function QTip(target, options, id, attr)
1124
1140
  else if(PLUGINS.imagemap && target.is('area')) {
1125
1141
  adjusted = PLUGINS.imagemap(self, target, at, PLUGINS.viewport ? method : FALSE);
1126
1142
  }
1127
- else if(PLUGINS.svg && typeof target[0].xmlbase === 'string') {
1143
+ else if(PLUGINS.svg && target[0].ownerSVGElement) {
1128
1144
  adjusted = PLUGINS.svg(self, target, at, PLUGINS.viewport ? method : FALSE);
1129
1145
  }
1130
1146
 
1131
1147
  else {
1132
- targetWidth = target.outerWidth();
1133
- targetHeight = target.outerHeight();
1148
+ targetWidth = target.outerWidth(FALSE);
1149
+ targetHeight = target.outerHeight(FALSE);
1134
1150
 
1135
1151
  position = PLUGINS.offset(target, container);
1136
1152
  }
@@ -1146,9 +1162,8 @@ function QTip(target, options, id, attr)
1146
1162
  // Adjust for position.fixed tooltips (and also iOS scroll bug in v3.2-4.0 & v4.3-4.3.2)
1147
1163
  if((PLUGINS.iOS > 3.1 && PLUGINS.iOS < 4.1) ||
1148
1164
  (PLUGINS.iOS >= 4.3 && PLUGINS.iOS < 4.33) ||
1149
- (!PLUGINS.iOS && fixed)
1165
+ (!PLUGINS.iOS && type === 'fixed')
1150
1166
  ){
1151
- win = $(window);
1152
1167
  position.left -= win.scrollLeft();
1153
1168
  position.top -= win.scrollTop();
1154
1169
  }
@@ -1177,7 +1192,7 @@ function QTip(target, options, id, attr)
1177
1192
  else { position.adjusted = { left: 0, top: 0 }; }
1178
1193
 
1179
1194
  // tooltipmove event
1180
- if(!triggerEvent('move', [position, viewport.elem || viewport], event)) { return self; }
1195
+ if(!self._triggerEvent('move', [position, viewport.elem || viewport], event)) { return self; }
1181
1196
  delete position.adjusted;
1182
1197
 
1183
1198
  // If effect is disabled, target it mouse, no animation is defined or positioning gives NaN out, set CSS directly
@@ -1197,73 +1212,20 @@ function QTip(target, options, id, attr)
1197
1212
  });
1198
1213
  }
1199
1214
 
1200
- // Set positioning flag
1215
+ // Set positioning flagwtf
1201
1216
  isPositioning = 0;
1202
1217
 
1203
1218
  return self;
1204
1219
  },
1205
1220
 
1206
- // Max/min width simulator function for all browsers.. yeaaah!
1207
- redraw: function()
1208
- {
1209
- if(self.rendered < 1 || isDrawing) { return self; }
1210
-
1211
- var style = options.style,
1212
- container = options.position.container,
1213
- perc, width, max, min;
1214
-
1215
- // Set drawing flag
1216
- isDrawing = 1;
1217
-
1218
- // tooltipredraw event
1219
- triggerEvent('redraw');
1220
-
1221
- // If tooltip has a set height/width, just set it... like a boss!
1222
- if(style.height) { tooltip.css(HEIGHT, style.height); }
1223
- if(style.width) { tooltip.css(WIDTH, style.width); }
1224
-
1225
- // Simulate max/min width if not set width present...
1226
- else {
1227
- // Reset width and add fluid class
1228
- tooltip.css(WIDTH, '').appendTo(redrawContainer);
1229
-
1230
- // Grab our tooltip width (add 1 if odd so we don't get wrapping problems.. huzzah!)
1231
- width = tooltip.width();
1232
- if(width % 2 < 1) { width += 1; }
1233
-
1234
- // Grab our max/min properties
1235
- max = tooltip.css('max-width') || '';
1236
- min = tooltip.css('min-width') || '';
1237
-
1238
- // Parse into proper pixel values
1239
- perc = (max + min).indexOf('%') > -1 ? container.width() / 100 : 0;
1240
- max = ((max.indexOf('%') > -1 ? perc : 1) * parseInt(max, 10)) || width;
1241
- min = ((min.indexOf('%') > -1 ? perc : 1) * parseInt(min, 10)) || 0;
1242
-
1243
- // Determine new dimension size based on max/min/current values
1244
- width = max + min ? Math.min(Math.max(width, min), max) : width;
1245
-
1246
- // Set the newly calculated width and remvoe fluid class
1247
- tooltip.css(WIDTH, Math.round(width)).appendTo(container);
1248
- }
1249
-
1250
- // tooltipredrawn event
1251
- triggerEvent('redrawn');
1252
-
1253
- // Set drawing flag
1254
- isDrawing = 0;
1255
-
1256
- return self;
1257
- },
1258
-
1259
1221
  disable: function(state)
1260
1222
  {
1261
1223
  if('boolean' !== typeof state) {
1262
- state = !(tooltip.hasClass(disabled) || cache.disabled);
1224
+ state = !(tooltip.hasClass(disabledClass) || cache.disabled);
1263
1225
  }
1264
1226
 
1265
1227
  if(self.rendered) {
1266
- tooltip.toggleClass(disabled, state);
1228
+ tooltip.toggleClass(disabledClass, state);
1267
1229
  $.attr(tooltip[0], 'aria-disabled', state);
1268
1230
  }
1269
1231
  else {
@@ -1509,7 +1471,7 @@ QTIP.bind = function(opts, event)
1509
1471
  * Also set onTarget when triggered to keep mouse tracking working
1510
1472
  */
1511
1473
  targets.show.bind('mousemove'+namespace, function(event) {
1512
- MOUSE = { pageX: event.pageX, pageY: event.pageY, type: 'mousemove' };
1474
+ storeMouse(event);
1513
1475
  api.cache.onTarget = TRUE;
1514
1476
  });
1515
1477
 
@@ -1546,7 +1508,8 @@ QTIP.bind = function(opts, event)
1546
1508
 
1547
1509
  // Prerendering is enabled, create tooltip now
1548
1510
  if(options.show.ready || options.prerender) { hoverIntent(event); }
1549
- });
1511
+ })
1512
+ .attr('data-hasqtip', TRUE);
1550
1513
  };
1551
1514
 
1552
1515
  // Setup base plugins
@@ -1580,7 +1543,8 @@ PLUGINS = QTIP.plugins = {
1580
1543
  // Custom (more correct for qTip!) offset calculator
1581
1544
  offset: function(elem, container) {
1582
1545
  var pos = elem.offset(),
1583
- docBody = elem.closest('body')[0],
1546
+ docBody = elem.closest('body'),
1547
+ quirks = $.browser.msie && document.compatMode !== 'CSS1Compat',
1584
1548
  parent = container, scrolled,
1585
1549
  coffset, overflow;
1586
1550
 
@@ -1605,8 +1569,10 @@ PLUGINS = QTIP.plugins = {
1605
1569
  }
1606
1570
  while((parent = $(parent[0].offsetParent)).length);
1607
1571
 
1608
- // Compensate for containers scroll if it also has an offsetParent
1609
- if(scrolled && scrolled[0] !== docBody) { scroll( scrolled, 1 ); }
1572
+ // Compensate for containers scroll if it also has an offsetParent (or in IE quirks mode)
1573
+ if(scrolled && scrolled[0] !== docBody[0] || quirks) {
1574
+ scroll( scrolled || docBody, 1 );
1575
+ }
1610
1576
  }
1611
1577
 
1612
1578
  return pos;
@@ -1709,6 +1675,7 @@ QTIP.defaults = {
1709
1675
  content: {
1710
1676
  text: TRUE,
1711
1677
  attr: 'title',
1678
+ deferred: FALSE,
1712
1679
  title: {
1713
1680
  text: FALSE,
1714
1681
  button: FALSE
@@ -1724,7 +1691,7 @@ QTIP.defaults = {
1724
1691
  x: 0, y: 0,
1725
1692
  mouse: TRUE,
1726
1693
  resize: TRUE,
1727
- method: 'flip flip'
1694
+ method: 'flipinvert flipinvert'
1728
1695
  },
1729
1696
  effect: function(api, pos, viewport) {
1730
1697
  $(this).animate(pos, {