compiler.js 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293
  1. /**
  2. * angular-strap
  3. * @version v2.3.5 - 2015-10-29
  4. * @link http://mgcrea.github.io/angular-strap
  5. * @author Olivier Louvignes <olivier@mg-crea.com> (https://github.com/mgcrea)
  6. * @license MIT License, http://www.opensource.org/licenses/MIT
  7. */
  8. 'use strict';
  9. angular.module('mgcrea.ngStrap.core', []).service('$bsCompiler', bsCompilerService);
  10. function bsCompilerService($q, $http, $injector, $compile, $controller, $templateCache) {
  11. this.compile = function(options) {
  12. if (options.template && /\.html$/.test(options.template)) {
  13. console.warn('Deprecated use of `template` option to pass a file. Please use the `templateUrl` option instead.');
  14. options.templateUrl = options.template;
  15. options.template = '';
  16. }
  17. var templateUrl = options.templateUrl;
  18. var template = options.template || '';
  19. var controller = options.controller;
  20. var controllerAs = options.controllerAs;
  21. var resolve = angular.copy(options.resolve || {});
  22. var locals = angular.copy(options.locals || {});
  23. var transformTemplate = options.transformTemplate || angular.identity;
  24. var bindToController = options.bindToController;
  25. angular.forEach(resolve, function(value, key) {
  26. if (angular.isString(value)) {
  27. resolve[key] = $injector.get(value);
  28. } else {
  29. resolve[key] = $injector.invoke(value);
  30. }
  31. });
  32. angular.extend(resolve, locals);
  33. if (template) {
  34. resolve.$template = $q.when(template);
  35. } else if (templateUrl) {
  36. resolve.$template = fetchTemplate(templateUrl);
  37. } else {
  38. throw new Error('Missing `template` / `templateUrl` option.');
  39. }
  40. if (options.contentTemplate) {
  41. resolve.$template = $q.all([ resolve.$template, fetchTemplate(options.contentTemplate) ]).then(function(templates) {
  42. var templateEl = angular.element(templates[0]);
  43. var contentEl = findElement('[ng-bind="content"]', templateEl[0]).removeAttr('ng-bind').html(templates[1]);
  44. if (!options.templateUrl) contentEl.next().remove();
  45. return templateEl[0].outerHTML;
  46. });
  47. }
  48. return $q.all(resolve).then(function(locals) {
  49. var template = transformTemplate(locals.$template);
  50. if (options.html) {
  51. template = template.replace(/ng-bind="/gi, 'ng-bind-html="');
  52. }
  53. var element = angular.element('<div>').html(template.trim()).contents();
  54. var linkFn = $compile(element);
  55. return {
  56. locals: locals,
  57. element: element,
  58. link: function link(scope) {
  59. locals.$scope = scope;
  60. if (controller) {
  61. var invokeCtrl = $controller(controller, locals, true);
  62. if (bindToController) {
  63. angular.extend(invokeCtrl.instance, locals);
  64. }
  65. var ctrl = angular.isObject(invokeCtrl) ? invokeCtrl : invokeCtrl();
  66. element.data('$ngControllerController', ctrl);
  67. element.children().data('$ngControllerController', ctrl);
  68. if (controllerAs) {
  69. scope[controllerAs] = ctrl;
  70. }
  71. }
  72. return linkFn.apply(null, arguments);
  73. }
  74. };
  75. });
  76. };
  77. function findElement(query, element) {
  78. return angular.element((element || document).querySelectorAll(query));
  79. }
  80. var fetchPromises = {};
  81. function fetchTemplate(template) {
  82. if (fetchPromises[template]) return fetchPromises[template];
  83. return fetchPromises[template] = $http.get(template, {
  84. cache: $templateCache
  85. }).then(function(res) {
  86. return res.data;
  87. });
  88. }
  89. }
  90. bsCompilerService.$inject = [ '$q', '$http', '$injector', '$compile', '$controller', '$templateCache' ];