<!DOCTYPE html>
<html ng-app="myApp">

  <head>
    <link data-require="bootstrap-css@2.3.2" data-semver="2.3.2" rel="stylesheet" href="//netdna.bootstrapcdn.com/twitter-bootstrap/2.3.2/css/bootstrap-combined.min.css" />
    <script data-require="angular.js@1.0.7" data-semver="1.0.7" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.7/angular.min.js"></script>
    <script data-require="angular-ui-bootstrap@0.4.0" data-semver="0.4.0" src="http://angular-ui.github.io/bootstrap/ui-bootstrap-tpls-0.4.0.min.js"></script>
    <link rel="stylesheet" href="style.css" />
    <script src="script.js"></script>
    <script src="customPopup.js"></script>
  </head>

  <body ng-controller="myCtrl">
  
    <div class="hero-unit demo-box span6 offset3 pagination-centered">
      <h2>Title: {{item.title}}</h2>
      <div iantooltip="Hi" iantooltip-title="item.title" iantooltip-placement="right">
        <button class="btn">{{text}}</button>
      </div>
      <div motopopover-title="Hi" motopopover-image="http://www.revillweb.com/wp-content/uploads/2013/12/square.png" motopopover-placement="left">
        <button class="btn">{{text}}</button>
      </div>
    </div>
    
  </body>

</html>

var app = angular.module('myApp', ['ui.bootstrap', 'ian.bootstrap']);

app.controller('myCtrl', function ($scope) {
  $scope.item = {
    title: 'Original Title'
  };

  $scope.text = 'Click me';
});
/* Styles go here */

.demo-box {
  margin-top: 100px;
}
angular.module("ian.bootstrap", ["ian.bootstrap.tooltip"]);


/**
 * The following features are still outstanding: animation as a
 * function, placement as a function, inside, support for more triggers than
 * just mouse enter/leave, html tooltips, and selector delegation.
 */
angular.module('ian.bootstrap.tooltip', [ 'ui.bootstrap.position' ])

/**
 * The $iantooltip service creates tooltip- and popover-like directives as well as
 * houses global options for them.
 */
  .provider('$iantooltip', function () {
    // The default options tooltip and popover.
    var defaultOptions = {
      placement: 'top',
      animation: true,
      popupDelay: 0
    };

    // Default hide triggers for each show trigger
    var triggerMap = {
      'mouseenter': 'mouseleave',
      'click': 'click',
      'focus': 'blur'
    };

    // The options specified to the provider globally.
    var globalOptions = {};

    /**
     * `options({})` allows global configuration of all tooltips in the
     * application.
     *
     *   var app = angular.module( 'App', ['ui.bootstrap.tooltip'], function( $iantooltipProvider ) {
   *     // place tooltips left instead of top by default
   *     $iantooltipProvider.options( { placement: 'left' } );
   *   });
     */
    this.options = function (value) {
      angular.extend(globalOptions, value);
    };

    /**
     * This allows you to extend the set of trigger mappings available. E.g.:
     *
     *   $iantooltipProvider.setTriggers( 'openTrigger': 'closeTrigger' );
     */
    this.setTriggers = function setTriggers (triggers) {
      angular.extend(triggerMap, triggers);
    };

    /**
     * This is a helper function for translating camel-case to snake-case.
     */
    function snake_case (name) {
      var regexp = /[A-Z]/g;
      var separator = '-';
      return name.replace(regexp, function (letter, pos) {
        return (pos ? separator : '') + letter.toLowerCase();
      });
    }

    //noinspection JSValidateTypes
    /**
     * Returns the actual instance of the $iantooltip service.
     * TODO support multiple triggers
     */
    this.$get = [ '$compile', '$timeout', '$parse', '$document', '$position', '$interpolate', function ($compile, $timeout, $parse, $document, $position, $interpolate) {
      return function $iantooltip (type, prefix, defaultTriggerShow) {
        var options = angular.extend({}, defaultOptions, globalOptions);

        function setTriggers (trigger) {
          var show, hide;

          show = trigger || options.trigger || defaultTriggerShow;
          if (angular.isDefined(options.trigger)) {
            hide = triggerMap[options.trigger] || show;
          } else {
            hide = triggerMap[show] || show;
          }

          return {
            show: show,
            hide: hide
          };
        }

        var directiveName = snake_case(type);
        var triggers = setTriggers(undefined);

        var startSym = $interpolate.startSymbol();
        var endSym = $interpolate.endSymbol();
        var template =
          '<' + directiveName + '-popup ' +
            'title="tt_title" ' +
            'content="' + startSym + 'tt_content' + endSym + '" ' +
            'placement="' + startSym + 'tt_placement' + endSym + '" ' +
            'animation="tt_animation()" ' +
            'is-open="tt_isOpen"' +
            '>' +
            '</' + directiveName + '-popup>';

        return {
          restrict: 'EA',
          scope: true,
          link: function link (scope, element, attrs) {
            var tooltip = $compile(template)(scope);
            var transitionTimeout;
            var popupTimeout;
            var $body;
            var appendToBody = angular.isDefined(options.appendToBody) ? options.appendToBody : false;

            scope.hide = function () {
              hide();
            }
            // By default, the tooltip is not open.
            // TODO add ability to start tooltip opened
            scope.tt_isOpen = false;

            function toggleTooltipBind () {
              if (!scope.tt_isOpen) {
                showTooltipBind();
              } else {
                hideTooltipBind();
              }
            }

            // Show the tooltip with delay if specified, otherwise show it immediately
            function showTooltipBind () {
              if (scope.tt_popupDelay) {
                popupTimeout = $timeout(show, scope.tt_popupDelay);
              } else {
                scope.$apply(show);
              }
            }

            function hideTooltipBind () {
              scope.$apply(function () {
                hide();
              });
            }

            // Show the tooltip popup element.
            function show () {
              var position,
                ttWidth,
                ttHeight,
                ttPosition;

              // Don't show empty tooltips.
              if (!scope.tt_content) {
                return;
              }

              // If there is a pending remove transition, we must cancel it, lest the
              // tooltip be mysteriously removed.
              if (transitionTimeout) {
                $timeout.cancel(transitionTimeout);
              }

              // Set the initial positioning.
              tooltip.css({ top: 0, left: 0, display: 'block' });

              // Now we add it to the DOM because need some info about it. But it's not
              // visible yet anyway.
              if (appendToBody) {
                $body = $body || $document.find('body');
                $body.append(tooltip);
              } else {
                element.after(tooltip);
              }

              // Get the position of the directive element.
              position = options.appendToBody ? $position.offset(element) : $position.position(element);

              // Get the height and width of the tooltip so we can center it.
              ttWidth = tooltip.prop('offsetWidth');
              ttHeight = tooltip.prop('offsetHeight');

              // Calculate the tooltip's top and left coordinates to center it with
              // this directive.
              switch (scope.tt_placement) {
                case 'mouse':
                  var mousePos = $position.mouse();
                  ttPosition = {
                    top: mousePos.y,
                    left: mousePos.x
                  };
                  break;
                case 'right':
                  ttPosition = {
                    top: position.top + position.height / 2 - ttHeight / 2,
                    left: position.left + position.width
                  };
                  break;
                case 'bottom':
                  ttPosition = {
                    top: position.top + position.height,
                    left: position.left + position.width / 2 - ttWidth / 2
                  };
                  break;
                case 'left':
                  ttPosition = {
                    top: position.top + position.height / 2 - ttHeight / 2,
                    left: position.left - ttWidth
                  };
                  break;
                default:
                  ttPosition = {
                    top: position.top - ttHeight,
                    left: position.left + position.width / 2 - ttWidth / 2
                  };
                  break;
              }

              ttPosition.top += 'px';
              ttPosition.left += 'px';

              // Now set the calculated positioning.
              tooltip.css(ttPosition);

              // And show the tooltip.
              scope.tt_isOpen = true;
            }

            // Hide the tooltip popup element.
            function hide () {
              // First things first: we don't show it anymore.
              scope.tt_isOpen = false;

              //if tooltip is going to be shown after delay, we must cancel this
              $timeout.cancel(popupTimeout);

              // And now we remove it from the DOM. However, if we have animation, we
              // need to wait for it to expire beforehand.
              // FIXME: this is a placeholder for a port of the transitions library.
              if (angular.isDefined(scope.tt_animation) && scope.tt_animation()) {
                transitionTimeout = $timeout(function () {
                  tooltip.remove();
                }, 500);
              } else {
                tooltip.remove();
              }
            }

            /**
             * Observe the relevant attributes.
             */

            attrs.$observe(prefix + 'Mediaid', function (val) {
              scope.tt_mediaid = val;
            });

            attrs.$observe(type, function (val) {
              scope.tt_content = val;
            });

            attrs.$observe(prefix + 'Title', function (val) {
              scope.tt_title = val;
            });

            attrs.$observe(prefix + 'Placement', function (val) {
              scope.tt_placement = angular.isDefined(val) ? val : options.placement;
            });

            attrs.$observe(prefix + 'Animation', function (val) {
              scope.tt_animation = angular.isDefined(val) ? $parse(val) : function () {
                return options.animation;
              };
            });

            attrs.$observe(prefix + 'PopupDelay', function (val) {
              var delay = parseInt(val, 10);
              scope.tt_popupDelay = !isNaN(delay) ? delay : options.popupDelay;
            });

            attrs.$observe(prefix + 'Trigger', function (val) {
              element.unbind(triggers.show);
              element.unbind(triggers.hide);

              triggers = setTriggers(val);

              if (triggers.show === triggers.hide) {
                element.bind(triggers.show, toggleTooltipBind);
              } else {
                element.bind(triggers.show, showTooltipBind);
                element.bind(triggers.hide, hideTooltipBind);
              }
            });

            attrs.$observe(prefix + 'AppendToBody', function (val) {
              appendToBody = angular.isDefined(val) ? $parse(val)(scope) : appendToBody;
            });

            // if a tooltip is attached to <body> we need to remove it on
            // location change as its parent scope will probably not be destroyed
            // by the change.
            if (appendToBody) {
              scope.$on('$locationChangeSuccess', function closeTooltipOnLocationChangeSuccess () {
                if (scope.tt_isOpen) {
                  hide();
                }
              });
            }

            // Make sure tooltip is destroyed and removed.
            scope.$on('$destroy', function onDestroyTooltip () {
              if (scope.tt_isOpen) {
                hide();
              } else {
                tooltip.remove();
              }
            });
          }
        };
      };
    }];
  })

  .directive('iantooltipPopup', function () {
    return {
      restrict: 'E',
      replace: true,
      scope: { mediaid: '@', title: '=', content: '@', placement: '@', animation: '&', isOpen: '&' },
      templateUrl: 'popover.html',
      link: function (scope, element, attrs) {
        scope.showForm = false;
      }
    };
  })
  .directive('motopopover', function () {
    return {
      restrict: 'E',
      replace: true,
      scope: { mediaid: '@', title: '=', image: "=", content: '@', placement: '@', animation: '&', isOpen: '&' },
      templateUrl: 'popover.html',
      link: function (scope, element, attrs) {
        //scope.showForm = false;
      }
    };
  })
/*  .directive('motopopover', [ '$motopopover', function ($motopopover) {
    return $motopopover('motopopover', 'motopopover', 'hover');
  })*/
  .directive('iantooltip', [ '$iantooltip', function ($iantooltip) {
    return $iantooltip('iantooltip', 'iantooltip', 'click');
  }]);
<div class="popover {{placement}}" ng-class="{ in: isOpen(), fade: animation() }">
  <div class="arrow"></div>
  <div class="popover-inner">
    <h3 class="popover-title">{{title}}</h3>
    <div class="popover-content">
          <img src="{{image}}"/>
    </div>
  </div>
</div>