Merge remote-tracking branch 'upstream/4.6' into 4.6-master-2015-05-13-15-51-23
[civicrm-core.git] / ang / crmUi.js
index de2e078246463eebb641ba66f27c32dbda3585d1..cd61238787bcc711f0d24e3f9acb906915047aa1 100644 (file)
@@ -6,7 +6,7 @@
   angular.module('crmUi', [])
 
     // example <div crm-ui-accordion crm-title="ts('My Title')" crm-collapsed="true">...content...</div>
-    // WISHLIST: crmCollapsed should support two-way/continous binding
+    // WISHLIST: crmCollapsed should support two-way/continuous binding
     .directive('crmUiAccordion', function() {
       return {
         scope: {
     // Example:
     //   <a ng-click="$broadcast('my-insert-target', 'some new text')>Insert</a>
     //   <textarea crm-ui-insert-rx='my-insert-target'></textarea>
-    // TODO Consider ways to separate the plain-text/rich-text implementations
     .directive('crmUiInsertRx', function() {
       return {
         link: function(scope, element, attrs) {
           scope.$on(attrs.crmUiInsertRx, function(e, tokenName) {
-            var id = element.attr('id');
-            if (CKEDITOR.instances[id]) {
-              CKEDITOR.instances[id].insertText(tokenName);
-              $(element).select2('close').select2('val', '');
-              CKEDITOR.instances[id].focus();
-            }
-            else {
-              var crmForEl = $('#' + id);
-              var origVal = crmForEl.val();
-              var origPos = crmForEl[0].selectionStart;
-              var newVal = origVal.substring(0, origPos) + tokenName + origVal.substring(origPos, origVal.length);
-              crmForEl.val(newVal);
-              var newPos = (origPos + tokenName.length);
-              crmForEl[0].selectionStart = newPos;
-              crmForEl[0].selectionEnd = newPos;
-
-              $(element).select2('close').select2('val', '');
-              crmForEl.triggerHandler('change');
-              crmForEl.focus();
-            }
+            CRM.wysiwyg.insert(element, tokenName);
+            $(element).select2('close').select2('val', '');
+            CRM.wysiwyg.focus(element);
           });
         }
       };
       return {
         require: '?ngModel',
         link: function (scope, elm, attr, ngModel) {
-          var ck = CKEDITOR.replace(elm[0]);
-
-          if (ck) {
-            _.extend(ck.config, {
-              width: '94%',
-              height: '400',
-              filebrowserBrowseUrl: CRM.crmUi.browseUrl + '?cms=civicrm&type=files',
-              filebrowserImageBrowseUrl: CRM.crmUi.browseUrl + '?cms=civicrm&type=images',
-              filebrowserFlashBrowseUrl: CRM.crmUi.browseUrl + '?cms=civicrm&type=flash',
-              filebrowserUploadUrl: CRM.crmUi.uploadUrl + '?cms=civicrm&type=files',
-              filebrowserImageUploadUrl: CRM.crmUi.uploadUrl + '?cms=civicrm&type=images',
-              filebrowserFlashUploadUrl: CRM.crmUi.uploadUrl + '?cms=civicrm&type=flash',
-            });
-          }
 
+          var editor = CRM.wysiwyg.create(elm);
           if (!ngModel) {
             return;
           }
 
           if (attr.ngBlur) {
-            ck.on('blur', function(){
-              $timeout(function(){
+            $(elm).on('blur', function() {
+              $timeout(function() {
                 scope.$eval(attr.ngBlur);
               });
             });
           }
 
-          ck.on('pasteState', function () {
-            scope.$apply(function () {
-              ngModel.$setViewValue(ck.getData());
+          $(elm).on('paste change keypress', function() {
+            scope.$apply(function() {
+              ngModel.$setViewValue(CRM.wysiwyg.getVal(elm));
             });
           });
 
-          ck.on('insertText', function () {
-            $timeout(function () {
-              ngModel.$setViewValue(ck.getData());
-            });
-          });
-
-          ngModel.$render = function (value) {
-            ck.setData(ngModel.$viewValue);
+          ngModel.$render = function(value) {
+            CRM.wysiwyg.setVal(elm, ngModel.$viewValue);
           };
         }
       };
           // In cases where UI initiates update, there may be an extra
           // call to refreshUI, but it doesn't create a cycle.
 
-          ngModel.$render = function () {
-            $timeout(function () {
-              // ex: msg_template_id adds new item then selects it; use $timeout to ensure that
-              // new item is added before selection is made
-              element.select2('val', ngModel.$viewValue);
-            });
-          };
+          if (ngModel) {
+            ngModel.$render = function () {
+              $timeout(function () {
+                // ex: msg_template_id adds new item then selects it; use $timeout to ensure that
+                // new item is added before selection is made
+                element.select2('val', ngModel.$viewValue);
+              });
+            };
+          }
           function refreshModel() {
             var oldValue = ngModel.$viewValue, newValue = element.select2('val');
             if (oldValue != newValue) {
           function init() {
             // TODO watch select2-options
             element.select2(scope.crmUiSelect || {});
-            element.on('change', refreshModel);
-            $timeout(ngModel.$render);
+            if (ngModel) {
+              element.on('change', refreshModel);
+              $timeout(ngModel.$render);
+            }
           }
 
           init();
           }
 
           function init() {
-            // TODO watch options
             // TODO can we infer "entity" from model?
             element.crmEntityRef(scope.crmEntityref || {});
             element.on('change', refreshModel);