1 // Generated by CoffeeScript 1.4.0
6 # More info at [www.opentip.org](http://www.opentip.org)
8 # Copyright (c) 2012, Matias Meno
9 # Graphics by Tjandra Mayerhold
11 # Permission is hereby granted, free of charge, to any person obtaining a copy
12 # of this software and associated documentation files (the "Software"), to deal
13 # in the Software without restriction, including without limitation the rights
14 # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
15 # copies of the Software, and to permit persons to whom the Software is
16 # furnished to do so, subject to the following conditions:
18 # The above copyright notice and this permission notice shall be included in
19 # all copies or substantial portions of the Software.
21 # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
24 # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
25 # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
26 # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
31 var Opentip, firstAdapter, i, mouseMoved, mousePosition, mousePositionObservers, position, vendors, _i, _len, _ref,
33 __indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; },
34 __hasProp = {}.hasOwnProperty;
36 Opentip = (function() {
38 Opentip.prototype.STICKS_OUT_TOP = 1;
40 Opentip.prototype.STICKS_OUT_BOTTOM = 2;
42 Opentip.prototype.STICKS_OUT_LEFT = 1;
44 Opentip.prototype.STICKS_OUT_RIGHT = 2;
46 Opentip.prototype["class"] = {
47 container: "opentip-container",
50 content: "ot-content",
51 loadingIndicator: "ot-loading-indicator",
53 goingToHide: "ot-going-to-hide",
56 goingToShow: "ot-going-to-show",
57 showing: "ot-showing",
58 visible: "ot-visible",
59 loading: "ot-loading",
60 ajaxError: "ot-ajax-error",
62 showEffectPrefix: "ot-show-effect-",
63 hideEffectPrefix: "ot-hide-effect-",
67 function Opentip(element, content, title, options) {
68 var elementsOpentips, hideTrigger, methodToBind, optionSources, prop, styleName, _i, _j, _len, _len1, _ref, _ref1, _ref2, _tmpStyle,
70 this.id = ++Opentip.lastId;
71 this.debug("Creating Opentip.");
72 Opentip.tips.push(this);
73 this.adapter = Opentip.adapter;
74 elementsOpentips = this.adapter.data(element, "opentips") || [];
75 elementsOpentips.push(this);
76 this.adapter.data(element, "opentips", elementsOpentips);
77 this.triggerElement = this.adapter.wrap(element);
78 if (this.triggerElement.length > 1) {
79 throw new Error("You can't call Opentip on multiple elements.");
81 if (this.triggerElement.length < 1) {
82 throw new Error("Invalid element.");
87 this.waitingToShow = false;
88 this.waitingToHide = false;
89 this.currentPosition = {
99 this.currentObservers = {
105 options = this.adapter.clone(options);
106 if (typeof content === "object") {
108 content = title = void 0;
109 } else if (typeof title === "object") {
114 options.title = title;
116 if (content != null) {
117 this.setContent(content);
119 if (options["extends"] == null) {
120 if (options.style != null) {
121 options["extends"] = options.style;
123 options["extends"] = Opentip.defaultStyle;
126 optionSources = [options];
128 while (_tmpStyle["extends"]) {
129 styleName = _tmpStyle["extends"];
130 _tmpStyle = Opentip.styles[styleName];
131 if (_tmpStyle == null) {
132 throw new Error("Invalid style: " + styleName);
134 optionSources.unshift(_tmpStyle);
135 if (!((_tmpStyle["extends"] != null) || styleName === "standard")) {
136 _tmpStyle["extends"] = "standard";
139 options = (_ref = this.adapter).extend.apply(_ref, [{}].concat(__slice.call(optionSources)));
140 options.hideTriggers = (function() {
141 var _i, _len, _ref1, _results;
142 _ref1 = options.hideTriggers;
144 for (_i = 0, _len = _ref1.length; _i < _len; _i++) {
145 hideTrigger = _ref1[_i];
146 _results.push(hideTrigger);
150 if (options.hideTrigger && options.hideTriggers.length === 0) {
151 options.hideTriggers.push(options.hideTrigger);
153 _ref1 = ["tipJoint", "targetJoint", "stem"];
154 for (_i = 0, _len = _ref1.length; _i < _len; _i++) {
156 if (options[prop] && typeof options[prop] === "string") {
157 options[prop] = new Opentip.Joint(options[prop]);
160 if (options.ajax && (options.ajax === true || !options.ajax)) {
161 if (this.adapter.tagName(this.triggerElement) === "A") {
162 options.ajax = this.adapter.attr(this.triggerElement, "href");
164 options.ajax = false;
167 if (options.showOn === "click" && this.adapter.tagName(this.triggerElement) === "A") {
168 this.adapter.observe(this.triggerElement, "click", function(e) {
171 return e.stopped = true;
174 if (options.target) {
175 options.fixed = true;
177 if (options.stem === true) {
178 options.stem = new Opentip.Joint(options.tipJoint);
180 if (options.target === true) {
181 options.target = this.triggerElement;
182 } else if (options.target) {
183 options.target = this.adapter.wrap(options.target);
185 this.currentStem = options.stem;
186 if (options.delay == null) {
187 options.delay = options.showOn === "mouseover" ? 0.2 : 0;
189 if (options.targetJoint == null) {
190 options.targetJoint = new Opentip.Joint(options.tipJoint).flip();
192 this.showTriggers = [];
193 this.showTriggersWhenVisible = [];
194 this.hideTriggers = [];
195 if (options.showOn && options.showOn !== "creation") {
196 this.showTriggers.push({
197 element: this.triggerElement,
198 event: options.showOn
201 if (options.ajaxCache != null) {
202 options.cache = options.ajaxCache;
203 delete options.ajaxCache;
205 this.options = options;
207 _ref2 = ["prepareToShow", "prepareToHide", "show", "hide", "reposition"];
208 for (_j = 0, _len1 = _ref2.length; _j < _len1; _j++) {
209 methodToBind = _ref2[_j];
210 this.bound[methodToBind] = (function(methodToBind) {
212 return _this[methodToBind].apply(_this, arguments);
216 this.adapter.domReady(function() {
218 if (_this.options.showOn === "creation") {
219 return _this.prepareToShow();
224 Opentip.prototype._setup = function() {
225 var hideOn, hideTrigger, hideTriggerElement, i, _i, _j, _len, _len1, _ref, _ref1, _results;
226 this.debug("Setting up the tooltip.");
227 this._buildContainer();
228 this.hideTriggers = [];
229 _ref = this.options.hideTriggers;
230 for (i = _i = 0, _len = _ref.length; _i < _len; i = ++_i) {
231 hideTrigger = _ref[i];
232 hideTriggerElement = null;
233 hideOn = this.options.hideOn instanceof Array ? this.options.hideOn[i] : this.options.hideOn;
234 if (typeof hideTrigger === "string") {
235 switch (hideTrigger) {
237 hideOn = hideOn || "mouseout";
238 hideTriggerElement = this.triggerElement;
241 hideOn = hideOn || "mouseover";
242 hideTriggerElement = this.container;
245 hideOn = hideOn || "mouseover";
246 hideTriggerElement = this.options.target;
251 throw new Error("Unknown hide trigger: " + hideTrigger + ".");
254 hideOn = hideOn || "mouseover";
255 hideTriggerElement = this.adapter.wrap(hideTrigger);
257 if (hideTriggerElement) {
258 this.hideTriggers.push({
259 element: hideTriggerElement,
261 original: hideTrigger
265 _ref1 = this.hideTriggers;
267 for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) {
268 hideTrigger = _ref1[_j];
269 _results.push(this.showTriggersWhenVisible.push({
270 element: hideTrigger.element,
277 Opentip.prototype._buildContainer = function() {
278 this.container = this.adapter.create("<div id=\"opentip-" + this.id + "\" class=\"" + this["class"].container + " " + this["class"].hidden + " " + this["class"].stylePrefix + this.options.className + "\"></div>");
279 this.adapter.css(this.container, {
282 if (this.options.ajax) {
283 this.adapter.addClass(this.container, this["class"].loading);
285 if (this.options.fixed) {
286 this.adapter.addClass(this.container, this["class"].fixed);
288 if (this.options.showEffect) {
289 this.adapter.addClass(this.container, "" + this["class"].showEffectPrefix + this.options.showEffect);
291 if (this.options.hideEffect) {
292 return this.adapter.addClass(this.container, "" + this["class"].hideEffectPrefix + this.options.hideEffect);
296 Opentip.prototype._buildElements = function() {
297 var headerElement, titleElement;
298 this.tooltipElement = this.adapter.create("<div class=\"" + this["class"].opentip + "\"><div class=\"" + this["class"].header + "\"></div><div class=\"" + this["class"].content + "\"></div></div>");
299 this.backgroundCanvas = this.adapter.wrap(document.createElement("canvas"));
300 this.adapter.css(this.backgroundCanvas, {
303 if (typeof G_vmlCanvasManager !== "undefined" && G_vmlCanvasManager !== null) {
304 G_vmlCanvasManager.initElement(this.adapter.unwrap(this.backgroundCanvas));
306 headerElement = this.adapter.find(this.tooltipElement, "." + this["class"].header);
307 if (this.options.title) {
308 titleElement = this.adapter.create("<h1></h1>");
309 this.adapter.update(titleElement, this.options.title, this.options.escapeTitle);
310 this.adapter.append(headerElement, titleElement);
312 if (this.options.ajax && !this.loaded) {
313 this.adapter.append(this.tooltipElement, this.adapter.create("<div class=\"" + this["class"].loadingIndicator + "\"><span>↻</span></div>"));
315 if (__indexOf.call(this.options.hideTriggers, "closeButton") >= 0) {
316 this.closeButtonElement = this.adapter.create("<a href=\"javascript:undefined;\" class=\"" + this["class"].close + "\"><span>Close</span></a>");
317 this.adapter.append(headerElement, this.closeButtonElement);
319 this.adapter.append(this.container, this.backgroundCanvas);
320 this.adapter.append(this.container, this.tooltipElement);
321 this.adapter.append(document.body, this.container);
322 this._newContent = true;
323 return this.redraw = true;
326 Opentip.prototype.setContent = function(content) {
327 this.content = content;
328 this._newContent = true;
329 if (typeof this.content === "function") {
330 this._contentFunction = this.content;
333 this._contentFunction = null;
336 return this._updateElementContent();
340 Opentip.prototype._updateElementContent = function() {
342 if (this._newContent || (!this.options.cache && this._contentFunction)) {
343 contentDiv = this.adapter.find(this.container, "." + this["class"].content);
344 if (contentDiv != null) {
345 if (this._contentFunction) {
346 this.debug("Executing content function.");
347 this.content = this._contentFunction(this);
349 this.adapter.update(contentDiv, this.content, this.options.escapeContent);
351 this._newContent = false;
353 this._storeAndLockDimensions();
354 return this.reposition();
357 Opentip.prototype._storeAndLockDimensions = function() {
359 if (!this.container) {
362 prevDimension = this.dimensions;
363 this.adapter.css(this.container, {
368 this.dimensions = this.adapter.dimensions(this.container);
369 this.dimensions.width += 1;
370 this.adapter.css(this.container, {
371 width: "" + this.dimensions.width + "px",
372 top: "" + this.currentPosition.top + "px",
373 left: "" + this.currentPosition.left + "px"
375 if (!this._dimensionsEqual(this.dimensions, prevDimension)) {
381 Opentip.prototype.activate = function() {
382 return this._setupObservers("hidden", "hiding");
385 Opentip.prototype.deactivate = function() {
386 this.debug("Deactivating tooltip.");
388 return this._setupObservers("-showing", "-visible", "-hidden", "-hiding");
391 Opentip.prototype._setupObservers = function() {
392 var observeOrStop, removeObserver, state, states, trigger, _i, _j, _k, _l, _len, _len1, _len2, _len3, _ref, _ref1, _ref2,
394 states = 1 <= arguments.length ? __slice.call(arguments, 0) : [];
395 for (_i = 0, _len = states.length; _i < _len; _i++) {
397 removeObserver = false;
398 if (state.charAt(0) === "-") {
399 removeObserver = true;
400 state = state.substr(1);
402 if (this.currentObservers[state] === !removeObserver) {
405 this.currentObservers[state] = !removeObserver;
406 observeOrStop = function() {
407 var args, _ref, _ref1;
408 args = 1 <= arguments.length ? __slice.call(arguments, 0) : [];
409 if (removeObserver) {
410 return (_ref = _this.adapter).stopObserving.apply(_ref, args);
412 return (_ref1 = _this.adapter).observe.apply(_ref1, args);
417 _ref = this.hideTriggers;
418 for (_j = 0, _len1 = _ref.length; _j < _len1; _j++) {
420 observeOrStop(trigger.element, trigger.event, this.bound.prepareToHide);
422 observeOrStop((document.onresize != null ? document : window), "resize", this.bound.reposition);
423 observeOrStop(window, "scroll", this.bound.reposition);
426 _ref1 = this.showTriggersWhenVisible;
427 for (_k = 0, _len2 = _ref1.length; _k < _len2; _k++) {
429 observeOrStop(trigger.element, trigger.event, this.bound.prepareToShow);
433 _ref2 = this.showTriggers;
434 for (_l = 0, _len3 = _ref2.length; _l < _len3; _l++) {
436 observeOrStop(trigger.element, trigger.event, this.bound.prepareToShow);
442 throw new Error("Unknown state: " + state);
448 Opentip.prototype.prepareToShow = function() {
450 this._abortShowing();
454 this.debug("Showing in " + this.options.delay + "s.");
455 if (this.container == null) {
458 if (this.options.group) {
459 Opentip._abortShowingGroup(this.options.group, this);
461 this.preparingToShow = true;
462 this._setupObservers("-hidden", "-hiding", "showing");
463 this._followMousePosition();
464 if (this.options.fixed && !this.options.target) {
465 this.initialMousePosition = mousePosition;
468 return this._showTimeoutId = this.setTimeout(this.bound.show, this.options.delay || 0);
471 Opentip.prototype.show = function() {
477 this._clearTimeouts();
478 if (!this._triggerElementExists()) {
479 return this.deactivate();
481 this.debug("Showing now.");
482 if (this.container == null) {
485 if (this.options.group) {
486 Opentip._hideGroup(this.options.group, this);
489 this.preparingToShow = false;
490 if (this.tooltipElement == null) {
491 this._buildElements();
493 this._updateElementContent();
494 if (this.options.ajax && (!this.loaded || !this.options.cache)) {
497 this._searchAndActivateCloseButtons();
498 this._startEnsureTriggerElement();
499 this.adapter.css(this.container, {
500 zIndex: Opentip.lastZIndex++
502 this._setupObservers("-hidden", "-hiding", "-showing", "-visible", "showing", "visible");
503 if (this.options.fixed && !this.options.target) {
504 this.initialMousePosition = mousePosition;
507 this.adapter.removeClass(this.container, this["class"].hiding);
508 this.adapter.removeClass(this.container, this["class"].hidden);
509 this.adapter.addClass(this.container, this["class"].goingToShow);
510 this.setCss3Style(this.container, {
511 transitionDuration: "0s"
513 this.defer(function() {
515 if (!_this.visible || _this.preparingToHide) {
518 _this.adapter.removeClass(_this.container, _this["class"].goingToShow);
519 _this.adapter.addClass(_this.container, _this["class"].showing);
521 if (_this.options.showEffect && _this.options.showEffectDuration) {
522 delay = _this.options.showEffectDuration;
524 _this.setCss3Style(_this.container, {
525 transitionDuration: "" + delay + "s"
527 _this._visibilityStateTimeoutId = _this.setTimeout(function() {
528 _this.adapter.removeClass(_this.container, _this["class"].showing);
529 return _this.adapter.addClass(_this.container, _this["class"].visible);
531 return _this._activateFirstInput();
536 Opentip.prototype._abortShowing = function() {
537 if (this.preparingToShow) {
538 this.debug("Aborting showing.");
539 this._clearTimeouts();
540 this._stopFollowingMousePosition();
541 this.preparingToShow = false;
542 return this._setupObservers("-showing", "-visible", "hiding", "hidden");
546 Opentip.prototype.prepareToHide = function() {
547 this._abortShowing();
552 this.debug("Hiding in " + this.options.hideDelay + "s");
553 this.preparingToHide = true;
554 this._setupObservers("-showing", "visible", "-hidden", "hiding");
555 return this._hideTimeoutId = this.setTimeout(this.bound.hide, this.options.hideDelay);
558 Opentip.prototype.hide = function() {
560 this._abortShowing();
564 this._clearTimeouts();
565 this.debug("Hiding!");
566 this.visible = false;
567 this.preparingToHide = false;
568 this._stopEnsureTriggerElement();
569 this._setupObservers("-showing", "-visible", "-hiding", "-hidden", "hiding", "hidden");
570 if (!this.options.fixed) {
571 this._stopFollowingMousePosition();
573 if (!this.container) {
576 this.adapter.removeClass(this.container, this["class"].visible);
577 this.adapter.removeClass(this.container, this["class"].showing);
578 this.adapter.addClass(this.container, this["class"].goingToHide);
579 this.setCss3Style(this.container, {
580 transitionDuration: "0s"
582 return this.defer(function() {
584 _this.adapter.removeClass(_this.container, _this["class"].goingToHide);
585 _this.adapter.addClass(_this.container, _this["class"].hiding);
587 if (_this.options.hideEffect && _this.options.hideEffectDuration) {
588 hideDelay = _this.options.hideEffectDuration;
590 _this.setCss3Style(_this.container, {
591 transitionDuration: "" + hideDelay + "s"
593 return _this._visibilityStateTimeoutId = _this.setTimeout(function() {
594 _this.adapter.removeClass(_this.container, _this["class"].hiding);
595 _this.adapter.addClass(_this.container, _this["class"].hidden);
596 _this.setCss3Style(_this.container, {
597 transitionDuration: "0s"
599 if (_this.options.removeElementsOnHide) {
600 _this.debug("Removing HTML elements.");
601 _this.adapter.remove(_this.container);
602 delete _this.container;
603 return delete _this.tooltipElement;
609 Opentip.prototype._abortHiding = function() {
610 if (this.preparingToHide) {
611 this.debug("Aborting hiding.");
612 this._clearTimeouts();
613 this.preparingToHide = false;
614 return this._setupObservers("-hiding", "showing", "visible");
618 Opentip.prototype.reposition = function() {
619 var position, stem, _ref,
621 position = this.getPosition();
622 if (position == null) {
625 stem = this.options.stem;
626 if (this.options.containInViewport) {
627 _ref = this._ensureViewportContainment(position), position = _ref.position, stem = _ref.stem;
629 if (this._positionsEqual(position, this.currentPosition)) {
632 if (!(!this.options.stem || stem.eql(this.currentStem))) {
635 this.currentPosition = position;
636 this.currentStem = stem;
638 this.adapter.css(this.container, {
639 left: "" + position.left + "px",
640 top: "" + position.top + "px"
642 return this.defer(function() {
643 var rawContainer, redrawFix;
644 rawContainer = _this.adapter.unwrap(_this.container);
645 rawContainer.style.visibility = "hidden";
646 redrawFix = rawContainer.offsetHeight;
647 return rawContainer.style.visibility = "visible";
651 Opentip.prototype.getPosition = function(tipJoint, targetJoint, stem) {
652 var additionalHorizontal, additionalVertical, offsetDistance, position, stemLength, targetDimensions, targetPosition, unwrappedTarget, _ref;
653 if (!this.container) {
656 if (tipJoint == null) {
657 tipJoint = this.options.tipJoint;
659 if (targetJoint == null) {
660 targetJoint = this.options.targetJoint;
663 if (this.options.target) {
664 targetPosition = this.adapter.offset(this.options.target);
665 targetDimensions = this.adapter.dimensions(this.options.target);
666 position = targetPosition;
667 if (targetJoint.right) {
668 unwrappedTarget = this.adapter.unwrap(this.options.target);
669 if (unwrappedTarget.getBoundingClientRect != null) {
670 position.left = unwrappedTarget.getBoundingClientRect().right + ((_ref = window.pageXOffset) != null ? _ref : document.body.scrollLeft);
672 position.left += targetDimensions.width;
674 } else if (targetJoint.center) {
675 position.left += Math.round(targetDimensions.width / 2);
677 if (targetJoint.bottom) {
678 position.top += targetDimensions.height;
679 } else if (targetJoint.middle) {
680 position.top += Math.round(targetDimensions.height / 2);
682 if (this.options.borderWidth) {
683 if (this.options.tipJoint.left) {
684 position.left += this.options.borderWidth;
686 if (this.options.tipJoint.right) {
687 position.left -= this.options.borderWidth;
689 if (this.options.tipJoint.top) {
690 position.top += this.options.borderWidth;
691 } else if (this.options.tipJoint.bottom) {
692 position.top -= this.options.borderWidth;
696 if (this.initialMousePosition) {
698 top: this.initialMousePosition.y,
699 left: this.initialMousePosition.x
703 top: mousePosition.y,
704 left: mousePosition.x
708 if (this.options.autoOffset) {
709 stemLength = this.options.stem ? this.options.stemLength : 0;
710 offsetDistance = stemLength && this.options.fixed ? 2 : 10;
711 additionalHorizontal = tipJoint.middle && !this.options.fixed ? 15 : 0;
712 additionalVertical = tipJoint.center && !this.options.fixed ? 15 : 0;
713 if (tipJoint.right) {
714 position.left -= offsetDistance + additionalHorizontal;
715 } else if (tipJoint.left) {
716 position.left += offsetDistance + additionalHorizontal;
718 if (tipJoint.bottom) {
719 position.top -= offsetDistance + additionalVertical;
720 } else if (tipJoint.top) {
721 position.top += offsetDistance + additionalVertical;
725 stem = this.options.stem;
728 position.left -= stemLength;
729 } else if (stem.left) {
730 position.left += stemLength;
733 position.top -= stemLength;
734 } else if (stem.top) {
735 position.top += stemLength;
739 position.left += this.options.offset[0];
740 position.top += this.options.offset[1];
741 if (tipJoint.right) {
742 position.left -= this.dimensions.width;
743 } else if (tipJoint.center) {
744 position.left -= Math.round(this.dimensions.width / 2);
746 if (tipJoint.bottom) {
747 position.top -= this.dimensions.height;
748 } else if (tipJoint.middle) {
749 position.top -= Math.round(this.dimensions.height / 2);
754 Opentip.prototype._ensureViewportContainment = function(position) {
755 var needsRepositioning, newSticksOut, originals, revertedX, revertedY, scrollOffset, stem, sticksOut, targetJoint, tipJoint, viewportDimensions, viewportPosition;
756 stem = this.options.stem;
761 if (!(this.visible && position)) {
764 sticksOut = this._sticksOut(position);
765 if (!(sticksOut[0] || sticksOut[1])) {
768 tipJoint = new Opentip.Joint(this.options.tipJoint);
769 if (this.options.targetJoint) {
770 targetJoint = new Opentip.Joint(this.options.targetJoint);
772 scrollOffset = this.adapter.scrollOffset();
773 viewportDimensions = this.adapter.viewportDimensions();
774 viewportPosition = [position.left - scrollOffset[0], position.top - scrollOffset[1]];
775 needsRepositioning = false;
776 if (viewportDimensions.width >= this.dimensions.width) {
778 needsRepositioning = true;
779 switch (sticksOut[0]) {
780 case this.STICKS_OUT_LEFT:
781 tipJoint.setHorizontal("left");
782 if (this.options.targetJoint) {
783 targetJoint.setHorizontal("right");
786 case this.STICKS_OUT_RIGHT:
787 tipJoint.setHorizontal("right");
788 if (this.options.targetJoint) {
789 targetJoint.setHorizontal("left");
794 if (viewportDimensions.height >= this.dimensions.height) {
796 needsRepositioning = true;
797 switch (sticksOut[1]) {
798 case this.STICKS_OUT_TOP:
799 tipJoint.setVertical("top");
800 if (this.options.targetJoint) {
801 targetJoint.setVertical("bottom");
804 case this.STICKS_OUT_BOTTOM:
805 tipJoint.setVertical("bottom");
806 if (this.options.targetJoint) {
807 targetJoint.setVertical("top");
812 if (!needsRepositioning) {
815 if (this.options.stem) {
818 position = this.getPosition(tipJoint, targetJoint, stem);
819 newSticksOut = this._sticksOut(position);
822 if (newSticksOut[0] && (newSticksOut[0] !== sticksOut[0])) {
824 tipJoint.setHorizontal(this.options.tipJoint.horizontal);
825 if (this.options.targetJoint) {
826 targetJoint.setHorizontal(this.options.targetJoint.horizontal);
829 if (newSticksOut[1] && (newSticksOut[1] !== sticksOut[1])) {
831 tipJoint.setVertical(this.options.tipJoint.vertical);
832 if (this.options.targetJoint) {
833 targetJoint.setVertical(this.options.targetJoint.vertical);
836 if (revertedX && revertedY) {
839 if (revertedX || revertedY) {
840 if (this.options.stem) {
843 position = this.getPosition(tipJoint, targetJoint, stem);
851 Opentip.prototype._sticksOut = function(position) {
852 var positionOffset, scrollOffset, sticksOut, viewportDimensions;
853 scrollOffset = this.adapter.scrollOffset();
854 viewportDimensions = this.adapter.viewportDimensions();
855 positionOffset = [position.left - scrollOffset[0], position.top - scrollOffset[1]];
856 sticksOut = [false, false];
857 if (positionOffset[0] < 0) {
858 sticksOut[0] = this.STICKS_OUT_LEFT;
859 } else if (positionOffset[0] + this.dimensions.width > viewportDimensions.width) {
860 sticksOut[0] = this.STICKS_OUT_RIGHT;
862 if (positionOffset[1] < 0) {
863 sticksOut[1] = this.STICKS_OUT_TOP;
864 } else if (positionOffset[1] + this.dimensions.height > viewportDimensions.height) {
865 sticksOut[1] = this.STICKS_OUT_BOTTOM;
870 Opentip.prototype._draw = function() {
871 var backgroundCanvas, bulge, canvasDimensions, canvasPosition, closeButton, closeButtonInner, closeButtonOuter, ctx, drawCorner, drawLine, hb, position, stemBase, stemLength, _i, _len, _ref, _ref1, _ref2,
873 if (!(this.backgroundCanvas && this.redraw)) {
876 this.debug("Drawing background.");
878 if (this.currentStem) {
879 _ref = ["top", "right", "bottom", "left"];
880 for (_i = 0, _len = _ref.length; _i < _len; _i++) {
882 this.adapter.removeClass(this.container, "stem-" + position);
884 this.adapter.addClass(this.container, "stem-" + this.currentStem.horizontal);
885 this.adapter.addClass(this.container, "stem-" + this.currentStem.vertical);
887 closeButtonInner = [0, 0];
888 closeButtonOuter = [0, 0];
889 if (__indexOf.call(this.options.hideTriggers, "closeButton") >= 0) {
890 closeButton = new Opentip.Joint(((_ref1 = this.currentStem) != null ? _ref1.toString() : void 0) === "top right" ? "top left" : "top right");
891 closeButtonInner = [this.options.closeButtonRadius + this.options.closeButtonOffset[0], this.options.closeButtonRadius + this.options.closeButtonOffset[1]];
892 closeButtonOuter = [this.options.closeButtonRadius - this.options.closeButtonOffset[0], this.options.closeButtonRadius - this.options.closeButtonOffset[1]];
894 canvasDimensions = this.adapter.clone(this.dimensions);
895 canvasPosition = [0, 0];
896 if (this.options.borderWidth) {
897 canvasDimensions.width += this.options.borderWidth * 2;
898 canvasDimensions.height += this.options.borderWidth * 2;
899 canvasPosition[0] -= this.options.borderWidth;
900 canvasPosition[1] -= this.options.borderWidth;
902 if (this.options.shadow) {
903 canvasDimensions.width += this.options.shadowBlur * 2;
904 canvasDimensions.width += Math.max(0, this.options.shadowOffset[0] - this.options.shadowBlur * 2);
905 canvasDimensions.height += this.options.shadowBlur * 2;
906 canvasDimensions.height += Math.max(0, this.options.shadowOffset[1] - this.options.shadowBlur * 2);
907 canvasPosition[0] -= Math.max(0, this.options.shadowBlur - this.options.shadowOffset[0]);
908 canvasPosition[1] -= Math.max(0, this.options.shadowBlur - this.options.shadowOffset[1]);
916 if (this.currentStem) {
917 if (this.currentStem.left) {
918 bulge.left = this.options.stemLength;
919 } else if (this.currentStem.right) {
920 bulge.right = this.options.stemLength;
922 if (this.currentStem.top) {
923 bulge.top = this.options.stemLength;
924 } else if (this.currentStem.bottom) {
925 bulge.bottom = this.options.stemLength;
929 if (closeButton.left) {
930 bulge.left = Math.max(bulge.left, closeButtonOuter[0]);
931 } else if (closeButton.right) {
932 bulge.right = Math.max(bulge.right, closeButtonOuter[0]);
934 if (closeButton.top) {
935 bulge.top = Math.max(bulge.top, closeButtonOuter[1]);
936 } else if (closeButton.bottom) {
937 bulge.bottom = Math.max(bulge.bottom, closeButtonOuter[1]);
940 canvasDimensions.width += bulge.left + bulge.right;
941 canvasDimensions.height += bulge.top + bulge.bottom;
942 canvasPosition[0] -= bulge.left;
943 canvasPosition[1] -= bulge.top;
944 if (this.currentStem && this.options.borderWidth) {
945 _ref2 = this._getPathStemMeasures(this.options.stemBase, this.options.stemLength, this.options.borderWidth), stemLength = _ref2.stemLength, stemBase = _ref2.stemBase;
947 backgroundCanvas = this.adapter.unwrap(this.backgroundCanvas);
948 backgroundCanvas.width = canvasDimensions.width;
949 backgroundCanvas.height = canvasDimensions.height;
950 this.adapter.css(this.backgroundCanvas, {
951 width: "" + backgroundCanvas.width + "px",
952 height: "" + backgroundCanvas.height + "px",
953 left: "" + canvasPosition[0] + "px",
954 top: "" + canvasPosition[1] + "px"
956 ctx = backgroundCanvas.getContext("2d");
957 ctx.setTransform(1, 0, 0, 1, 0, 0);
958 ctx.clearRect(0, 0, backgroundCanvas.width, backgroundCanvas.height);
960 ctx.fillStyle = this._getColor(ctx, this.dimensions, this.options.background, this.options.backgroundGradientHorizontal);
961 ctx.lineJoin = "miter";
962 ctx.miterLimit = 500;
963 hb = this.options.borderWidth / 2;
964 if (this.options.borderWidth) {
965 ctx.strokeStyle = this.options.borderColor;
966 ctx.lineWidth = this.options.borderWidth;
968 stemLength = this.options.stemLength;
969 stemBase = this.options.stemBase;
971 if (stemBase == null) {
974 drawLine = function(length, stem, first) {
976 ctx.moveTo(Math.max(stemBase, _this.options.borderRadius, closeButtonInner[0]) + 1 - hb, -hb);
979 ctx.lineTo(length / 2 - stemBase / 2, -hb);
980 ctx.lineTo(length / 2, -stemLength - hb);
981 return ctx.lineTo(length / 2 + stemBase / 2, -hb);
984 drawCorner = function(stem, closeButton, i) {
985 var angle1, angle2, innerWidth, offset;
987 ctx.lineTo(-stemBase + hb, 0 - hb);
988 ctx.lineTo(stemLength + hb, -stemLength - hb);
989 return ctx.lineTo(hb, stemBase - hb);
990 } else if (closeButton) {
991 offset = _this.options.closeButtonOffset;
992 innerWidth = closeButtonInner[0];
994 offset = [offset[1], offset[0]];
995 innerWidth = closeButtonInner[1];
997 angle1 = Math.acos(offset[1] / _this.options.closeButtonRadius);
998 angle2 = Math.acos(offset[0] / _this.options.closeButtonRadius);
999 ctx.lineTo(-innerWidth + hb, -hb);
1000 return ctx.arc(hb - offset[0], -hb + offset[1], _this.options.closeButtonRadius, -(Math.PI / 2 + angle1), angle2, false);
1002 ctx.lineTo(-_this.options.borderRadius + hb, -hb);
1003 return ctx.quadraticCurveTo(hb, -hb, hb, _this.options.borderRadius - hb);
1006 ctx.translate(-canvasPosition[0], -canvasPosition[1]);
1009 var cornerStem, i, lineLength, lineStem, positionIdx, positionX, positionY, rotation, _j, _ref3, _results;
1011 for (i = _j = 0, _ref3 = Opentip.positions.length / 2; 0 <= _ref3 ? _j < _ref3 : _j > _ref3; i = 0 <= _ref3 ? ++_j : --_j) {
1012 positionIdx = i * 2;
1013 positionX = i === 0 || i === 3 ? 0 : _this.dimensions.width;
1014 positionY = i < 2 ? 0 : _this.dimensions.height;
1015 rotation = (Math.PI / 2) * i;
1016 lineLength = i % 2 === 0 ? _this.dimensions.width : _this.dimensions.height;
1017 lineStem = new Opentip.Joint(Opentip.positions[positionIdx]);
1018 cornerStem = new Opentip.Joint(Opentip.positions[positionIdx + 1]);
1020 ctx.translate(positionX, positionY);
1021 ctx.rotate(rotation);
1022 drawLine(lineLength, lineStem.eql(_this.currentStem), i === 0);
1023 ctx.translate(lineLength, 0);
1024 drawCorner(cornerStem.eql(_this.currentStem), cornerStem.eql(closeButton), i);
1025 _results.push(ctx.restore());
1031 if (this.options.shadow) {
1032 ctx.shadowColor = this.options.shadowColor;
1033 ctx.shadowBlur = this.options.shadowBlur;
1034 ctx.shadowOffsetX = this.options.shadowOffset[0];
1035 ctx.shadowOffsetY = this.options.shadowOffset[1];
1039 if (this.options.borderWidth) {
1044 return (function() {
1045 var crossCenter, crossHeight, crossWidth, hcs, linkCenter;
1046 crossWidth = crossHeight = _this.options.closeButtonRadius * 2;
1047 if (closeButton.toString() === "top right") {
1048 linkCenter = [_this.dimensions.width - _this.options.closeButtonOffset[0], _this.options.closeButtonOffset[1]];
1049 crossCenter = [linkCenter[0] + hb, linkCenter[1] - hb];
1051 linkCenter = [_this.options.closeButtonOffset[0], _this.options.closeButtonOffset[1]];
1052 crossCenter = [linkCenter[0] - hb, linkCenter[1] - hb];
1054 ctx.translate(crossCenter[0], crossCenter[1]);
1055 hcs = _this.options.closeButtonCrossSize / 2;
1058 ctx.strokeStyle = _this.options.closeButtonCrossColor;
1059 ctx.lineWidth = _this.options.closeButtonCrossLineWidth;
1060 ctx.lineCap = "round";
1061 ctx.moveTo(-hcs, -hcs);
1062 ctx.lineTo(hcs, hcs);
1065 ctx.moveTo(hcs, -hcs);
1066 ctx.lineTo(-hcs, hcs);
1069 return _this.adapter.css(_this.closeButtonElement, {
1070 left: "" + (linkCenter[0] - hcs - _this.options.closeButtonLinkOverscan) + "px",
1071 top: "" + (linkCenter[1] - hcs - _this.options.closeButtonLinkOverscan) + "px",
1072 width: "" + (_this.options.closeButtonCrossSize + _this.options.closeButtonLinkOverscan * 2) + "px",
1073 height: "" + (_this.options.closeButtonCrossSize + _this.options.closeButtonLinkOverscan * 2) + "px"
1079 Opentip.prototype._getPathStemMeasures = function(outerStemBase, outerStemLength, borderWidth) {
1080 var angle, distanceBetweenTips, halfAngle, hb, rhombusSide, stemBase, stemLength;
1081 hb = borderWidth / 2;
1082 halfAngle = Math.atan((outerStemBase / 2) / outerStemLength);
1083 angle = halfAngle * 2;
1084 rhombusSide = hb / Math.sin(angle);
1085 distanceBetweenTips = 2 * rhombusSide * Math.cos(halfAngle);
1086 stemLength = hb + outerStemLength - distanceBetweenTips;
1087 if (stemLength < 0) {
1088 throw new Error("Sorry but your stemLength / stemBase ratio is strange.");
1090 stemBase = (Math.tan(halfAngle) * stemLength) * 2;
1092 stemLength: stemLength,
1097 Opentip.prototype._getColor = function(ctx, dimensions, color, horizontal) {
1098 var colorStop, gradient, i, _i, _len;
1099 if (horizontal == null) {
1102 if (typeof color === "string") {
1106 gradient = ctx.createLinearGradient(0, 0, dimensions.width, 0);
1108 gradient = ctx.createLinearGradient(0, 0, 0, dimensions.height);
1110 for (i = _i = 0, _len = color.length; _i < _len; i = ++_i) {
1111 colorStop = color[i];
1112 gradient.addColorStop(colorStop[0], colorStop[1]);
1117 Opentip.prototype._searchAndActivateCloseButtons = function() {
1118 var element, _i, _len, _ref;
1119 _ref = this.adapter.findAll(this.container, "." + this["class"].close);
1120 for (_i = 0, _len = _ref.length; _i < _len; _i++) {
1122 this.hideTriggers.push({
1123 element: this.adapter.wrap(element),
1127 if (this.currentObservers.showing) {
1128 this._setupObservers("-showing", "showing");
1130 if (this.currentObservers.visible) {
1131 return this._setupObservers("-visible", "visible");
1135 Opentip.prototype._activateFirstInput = function() {
1137 input = this.adapter.unwrap(this.adapter.find(this.container, "input, textarea"));
1138 return input != null ? typeof input.focus === "function" ? input.focus() : void 0 : void 0;
1141 Opentip.prototype._followMousePosition = function() {
1142 if (!this.options.fixed) {
1143 return Opentip._observeMousePosition(this.bound.reposition);
1147 Opentip.prototype._stopFollowingMousePosition = function() {
1148 if (!this.options.fixed) {
1149 return Opentip._stopObservingMousePosition(this.bound.reposition);
1153 Opentip.prototype._clearShowTimeout = function() {
1154 return clearTimeout(this._showTimeoutId);
1157 Opentip.prototype._clearHideTimeout = function() {
1158 return clearTimeout(this._hideTimeoutId);
1161 Opentip.prototype._clearTimeouts = function() {
1162 clearTimeout(this._visibilityStateTimeoutId);
1163 this._clearShowTimeout();
1164 return this._clearHideTimeout();
1167 Opentip.prototype._triggerElementExists = function() {
1169 el = this.adapter.unwrap(this.triggerElement);
1170 while (el.parentNode) {
1171 if (el.parentNode.tagName === "BODY") {
1179 Opentip.prototype._loadAjax = function() {
1184 this.loaded = false;
1185 this.loading = true;
1186 this.adapter.addClass(this.container, this["class"].loading);
1187 this.setContent("");
1188 this.debug("Loading content from " + this.options.ajax);
1189 return this.adapter.ajax({
1190 url: this.options.ajax,
1191 method: this.options.ajaxMethod,
1192 onSuccess: function(responseText) {
1193 _this.debug("Loading successful.");
1194 _this.adapter.removeClass(_this.container, _this["class"].loading);
1195 return _this.setContent(responseText);
1197 onError: function(error) {
1199 message = _this.options.ajaxErrorMessage;
1200 _this.debug(message, error);
1201 _this.setContent(message);
1202 return _this.adapter.addClass(_this.container, _this["class"].ajaxError);
1204 onComplete: function() {
1205 _this.adapter.removeClass(_this.container, _this["class"].loading);
1206 _this.loading = false;
1207 _this.loaded = true;
1208 _this._searchAndActivateCloseButtons();
1209 _this._activateFirstInput();
1210 return _this.reposition();
1215 Opentip.prototype._ensureTriggerElement = function() {
1216 if (!this._triggerElementExists()) {
1218 return this._stopEnsureTriggerElement();
1222 Opentip.prototype._ensureTriggerElementInterval = 1000;
1224 Opentip.prototype._startEnsureTriggerElement = function() {
1226 return this._ensureTriggerElementTimeoutId = setInterval((function() {
1227 return _this._ensureTriggerElement();
1228 }), this._ensureTriggerElementInterval);
1231 Opentip.prototype._stopEnsureTriggerElement = function() {
1232 return clearInterval(this._ensureTriggerElementTimeoutId);
1239 vendors = ["khtml", "ms", "o", "moz", "webkit"];
1241 Opentip.prototype.setCss3Style = function(element, styles) {
1242 var prop, value, vendor, vendorProp, _results;
1243 element = this.adapter.unwrap(element);
1245 for (prop in styles) {
1246 if (!__hasProp.call(styles, prop)) continue;
1247 value = styles[prop];
1248 if (element.style[prop] != null) {
1249 _results.push(element.style[prop] = value);
1251 _results.push((function() {
1252 var _i, _len, _results1;
1254 for (_i = 0, _len = vendors.length; _i < _len; _i++) {
1255 vendor = vendors[_i];
1256 vendorProp = "" + (this.ucfirst(vendor)) + (this.ucfirst(prop));
1257 if (element.style[vendorProp] != null) {
1258 _results1.push(element.style[vendorProp] = value);
1260 _results1.push(void 0);
1270 Opentip.prototype.defer = function(func) {
1271 return setTimeout(func, 0);
1274 Opentip.prototype.setTimeout = function(func, seconds) {
1275 return setTimeout(func, seconds ? seconds * 1000 : 0);
1278 Opentip.prototype.ucfirst = function(string) {
1279 if (string == null) {
1282 return string.charAt(0).toUpperCase() + string.slice(1);
1285 Opentip.prototype.dasherize = function(string) {
1286 return string.replace(/([A-Z])/g, function(_, character) {
1287 return "-" + (character.toLowerCase());
1291 mousePositionObservers = [];
1298 mouseMoved = function(e) {
1299 var observer, _i, _len, _results;
1300 mousePosition = Opentip.adapter.mousePosition(e);
1302 for (_i = 0, _len = mousePositionObservers.length; _i < _len; _i++) {
1303 observer = mousePositionObservers[_i];
1304 _results.push(observer());
1309 Opentip.followMousePosition = function() {
1310 return Opentip.adapter.observe(document.body, "mousemove", mouseMoved);
1313 Opentip._observeMousePosition = function(observer) {
1314 return mousePositionObservers.push(observer);
1317 Opentip._stopObservingMousePosition = function(removeObserver) {
1319 return mousePositionObservers = (function() {
1320 var _i, _len, _results;
1322 for (_i = 0, _len = mousePositionObservers.length; _i < _len; _i++) {
1323 observer = mousePositionObservers[_i];
1324 if (observer !== removeObserver) {
1325 _results.push(observer);
1332 Opentip.Joint = (function() {
1334 function Joint(pointerString) {
1335 if (pointerString == null) {
1338 if (pointerString instanceof Opentip.Joint) {
1339 pointerString = pointerString.toString();
1341 this.set(pointerString);
1346 Joint.prototype.set = function(string) {
1347 string = string.toLowerCase();
1348 this.setHorizontal(string);
1349 this.setVertical(string);
1353 Joint.prototype.setHorizontal = function(string) {
1354 var i, valid, _i, _j, _len, _len1, _results;
1355 valid = ["left", "center", "right"];
1356 for (_i = 0, _len = valid.length; _i < _len; _i++) {
1358 if (~string.indexOf(i)) {
1359 this.horizontal = i.toLowerCase();
1362 if (this.horizontal == null) {
1363 this.horizontal = "center";
1366 for (_j = 0, _len1 = valid.length; _j < _len1; _j++) {
1368 _results.push(this[i] = this.horizontal === i ? i : void 0);
1373 Joint.prototype.setVertical = function(string) {
1374 var i, valid, _i, _j, _len, _len1, _results;
1375 valid = ["top", "middle", "bottom"];
1376 for (_i = 0, _len = valid.length; _i < _len; _i++) {
1378 if (~string.indexOf(i)) {
1379 this.vertical = i.toLowerCase();
1382 if (this.vertical == null) {
1383 this.vertical = "middle";
1386 for (_j = 0, _len1 = valid.length; _j < _len1; _j++) {
1388 _results.push(this[i] = this.vertical === i ? i : void 0);
1393 Joint.prototype.eql = function(pointer) {
1394 return (pointer != null) && this.horizontal === pointer.horizontal && this.vertical === pointer.vertical;
1397 Joint.prototype.flip = function() {
1398 var flippedIndex, positionIdx;
1399 positionIdx = Opentip.position[this.toString(true)];
1400 flippedIndex = (positionIdx + 4) % 8;
1401 this.set(Opentip.positions[flippedIndex]);
1405 Joint.prototype.toString = function(camelized) {
1406 var horizontal, vertical;
1407 if (camelized == null) {
1410 vertical = this.vertical === "middle" ? "" : this.vertical;
1411 horizontal = this.horizontal === "center" ? "" : this.horizontal;
1412 if (vertical && horizontal) {
1414 horizontal = Opentip.prototype.ucfirst(horizontal);
1416 horizontal = " " + horizontal;
1419 return "" + vertical + horizontal;
1426 Opentip.prototype._positionsEqual = function(posA, posB) {
1427 return (posA != null) && (posB != null) && posA.left === posB.left && posA.top === posB.top;
1430 Opentip.prototype._dimensionsEqual = function(dimA, dimB) {
1431 return (dimA != null) && (dimB != null) && dimA.width === dimB.width && dimA.height === dimB.height;
1434 Opentip.prototype.debug = function() {
1436 args = 1 <= arguments.length ? __slice.call(arguments, 0) : [];
1437 if (Opentip.debug && ((typeof console !== "undefined" && console !== null ? console.debug : void 0) != null)) {
1438 args.unshift("#" + this.id + " |");
1439 return console.debug.apply(console, args);
1443 Opentip.findElements = function() {
1444 var adapter, content, element, optionName, optionValue, options, _i, _len, _ref, _results;
1445 adapter = Opentip.adapter;
1446 _ref = adapter.findAll(document.body, "[data-ot]");
1448 for (_i = 0, _len = _ref.length; _i < _len; _i++) {
1451 content = adapter.data(element, "ot");
1452 if (content === "" || content === "true" || content === "yes") {
1453 content = adapter.attr(element, "title");
1454 adapter.attr(element, "title", "");
1456 content = content || "";
1457 for (optionName in Opentip.styles.standard) {
1458 optionValue = adapter.data(element, "ot" + (Opentip.prototype.ucfirst(optionName)));
1459 if (optionValue != null) {
1460 if (optionValue === "yes" || optionValue === "true" || optionValue === "on") {
1462 } else if (optionValue === "no" || optionValue === "false" || optionValue === "off") {
1463 optionValue = false;
1465 options[optionName] = optionValue;
1468 _results.push(new Opentip(element, content, options));
1473 Opentip.version = "2.4.6";
1475 Opentip.debug = false;
1479 Opentip.lastZIndex = 100;
1483 Opentip._abortShowingGroup = function(group, originatingOpentip) {
1484 var opentip, _i, _len, _ref, _results;
1485 _ref = Opentip.tips;
1487 for (_i = 0, _len = _ref.length; _i < _len; _i++) {
1489 if (opentip !== originatingOpentip && opentip.options.group === group) {
1490 _results.push(opentip._abortShowing());
1492 _results.push(void 0);
1498 Opentip._hideGroup = function(group, originatingOpentip) {
1499 var opentip, _i, _len, _ref, _results;
1500 _ref = Opentip.tips;
1502 for (_i = 0, _len = _ref.length; _i < _len; _i++) {
1504 if (opentip !== originatingOpentip && opentip.options.group === group) {
1505 _results.push(opentip.hide());
1507 _results.push(void 0);
1513 Opentip.adapters = {};
1515 Opentip.adapter = null;
1517 firstAdapter = true;
1519 Opentip.addAdapter = function(adapter) {
1520 Opentip.adapters[adapter.name] = adapter;
1522 Opentip.adapter = adapter;
1523 adapter.domReady(Opentip.findElements);
1524 adapter.domReady(Opentip.followMousePosition);
1525 return firstAdapter = false;
1529 Opentip.positions = ["top", "topRight", "right", "bottomRight", "bottom", "bottomLeft", "left", "topLeft"];
1531 Opentip.position = {};
1533 _ref = Opentip.positions;
1534 for (i = _i = 0, _len = _ref.length; _i < _len; i = ++_i) {
1536 Opentip.position[position] = i;
1544 escapeContent: false,
1545 className: "standard",
1550 showOn: "mouseover",
1551 hideTrigger: "trigger",
1554 removeElementsOnHide: false,
1556 containInViewport: true,
1558 showEffect: "appear",
1560 showEffectDuration: 0.3,
1561 hideEffectDuration: 0.2,
1564 tipJoint: "top left",
1570 ajaxErrorMessage: "There was a problem downloading the content.",
1573 background: "#fff18f",
1574 backgroundGradientHorizontal: false,
1575 closeButtonOffset: [5, 5],
1576 closeButtonRadius: 7,
1577 closeButtonCrossSize: 4,
1578 closeButtonCrossColor: "#d2c35b",
1579 closeButtonCrossLineWidth: 1.5,
1580 closeButtonLinkOverscan: 6,
1583 borderColor: "#f2e37b",
1586 shadowOffset: [3, 3],
1587 shadowColor: "rgba(0, 0, 0, 0.1)"
1590 "extends": "standard",
1592 background: [[0, "rgba(252, 252, 252, 0.8)"], [0.5, "rgba(255, 255, 255, 0.8)"], [0.5, "rgba(250, 250, 250, 0.9)"], [1, "rgba(245, 245, 245, 0.9)"]],
1593 borderColor: "#eee",
1594 closeButtonCrossColor: "rgba(0, 0, 0, 0.2)",
1596 closeButtonRadius: 10,
1597 closeButtonOffset: [8, 8]
1600 "extends": "standard",
1603 borderColor: "#444",
1604 closeButtonCrossColor: "rgba(240, 240, 240, 1)",
1605 shadowColor: "rgba(0, 0, 0, 0.3)",
1606 shadowOffset: [2, 2],
1607 background: [[0, "rgba(30, 30, 30, 0.7)"], [0.5, "rgba(30, 30, 30, 0.8)"], [0.5, "rgba(10, 10, 10, 0.8)"], [1, "rgba(10, 10, 10, 0.9)"]]
1610 "extends": "standard",
1613 borderColor: "#AE0D11",
1614 closeButtonCrossColor: "rgba(255, 255, 255, 1)",
1615 shadowColor: "rgba(0, 0, 0, 0.3)",
1616 shadowOffset: [2, 2],
1617 background: [[0, "rgba(203, 15, 19, 0.7)"], [0.5, "rgba(203, 15, 19, 0.8)"], [0.5, "rgba(189, 14, 18, 0.8)"], [1, "rgba(179, 14, 17, 0.9)"]]
1621 Opentip.defaultStyle = "standard";
1623 if (typeof module !== "undefined" && module !== null) {
1624 module.exports = Opentip;
1626 window.Opentip = Opentip;
1630 // Generated by CoffeeScript 1.4.0
1631 var __slice = [].slice;
1635 $.fn.opentip = function(content, title, options) {
1636 return new Opentip(this, content, title, options);
1638 Adapter = (function() {
1640 function Adapter() {}
1642 Adapter.prototype.name = "jquery";
1644 Adapter.prototype.domReady = function(callback) {
1648 Adapter.prototype.create = function(html) {
1652 Adapter.prototype.wrap = function(element) {
1653 element = $(element);
1654 if (element.length > 1) {
1655 throw new Error("Multiple elements provided.");
1660 Adapter.prototype.unwrap = function(element) {
1661 return $(element)[0];
1664 Adapter.prototype.tagName = function(element) {
1665 return this.unwrap(element).tagName;
1668 Adapter.prototype.attr = function() {
1669 var args, element, _ref;
1670 element = arguments[0], args = 2 <= arguments.length ? __slice.call(arguments, 1) : [];
1671 return (_ref = $(element)).attr.apply(_ref, args);
1674 Adapter.prototype.data = function() {
1675 var args, element, _ref;
1676 element = arguments[0], args = 2 <= arguments.length ? __slice.call(arguments, 1) : [];
1677 return (_ref = $(element)).data.apply(_ref, args);
1680 Adapter.prototype.find = function(element, selector) {
1681 return $(element).find(selector).get(0);
1684 Adapter.prototype.findAll = function(element, selector) {
1685 return $(element).find(selector);
1688 Adapter.prototype.update = function(element, content, escape) {
1689 element = $(element);
1691 return element.text(content);
1693 return element.html(content);
1697 Adapter.prototype.append = function(element, child) {
1698 return $(element).append(child);
1701 Adapter.prototype.remove = function(element) {
1702 return $(element).remove();
1705 Adapter.prototype.addClass = function(element, className) {
1706 return $(element).addClass(className);
1709 Adapter.prototype.removeClass = function(element, className) {
1710 return $(element).removeClass(className);
1713 Adapter.prototype.css = function(element, properties) {
1714 return $(element).css(properties);
1717 Adapter.prototype.dimensions = function(element) {
1719 width: $(element).outerWidth(),
1720 height: $(element).outerHeight()
1724 Adapter.prototype.scrollOffset = function() {
1725 return [window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft, window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop];
1728 Adapter.prototype.viewportDimensions = function() {
1730 width: document.documentElement.clientWidth,
1731 height: document.documentElement.clientHeight
1735 Adapter.prototype.mousePosition = function(e) {
1745 Adapter.prototype.offset = function(element) {
1747 offset = $(element).offset();
1754 Adapter.prototype.observe = function(element, eventName, observer) {
1755 return $(element).bind(eventName, observer);
1758 Adapter.prototype.stopObserving = function(element, eventName, observer) {
1759 return $(element).unbind(eventName, observer);
1762 Adapter.prototype.ajax = function(options) {
1764 if (options.url == null) {
1765 throw new Error("No url provided");
1769 type: (_ref = (_ref1 = options.method) != null ? _ref1.toUpperCase() : void 0) != null ? _ref : "GET"
1770 }).done(function(content) {
1771 return typeof options.onSuccess === "function" ? options.onSuccess(content) : void 0;
1772 }).fail(function(request) {
1773 return typeof options.onError === "function" ? options.onError("Server responded with status " + request.status) : void 0;
1774 }).always(function() {
1775 return typeof options.onComplete === "function" ? options.onComplete() : void 0;
1779 Adapter.prototype.clone = function(object) {
1780 return $.extend({}, object);
1783 Adapter.prototype.extend = function() {
1784 var sources, target;
1785 target = arguments[0], sources = 2 <= arguments.length ? __slice.call(arguments, 1) : [];
1786 return $.extend.apply($, [target].concat(__slice.call(sources)));
1792 return Opentip.addAdapter(new Adapter);