Commit | Line | Data |
---|---|---|
030dce01 | 1 | (function (angular, $, _) { |
030dce01 | 2 | |
88e9e883 | 3 | angular.module('crmMailing', [ |
8443385d | 4 | 'crmUtil', 'crmAttachment', 'crmAutosave', 'ngRoute', 'ui.utils', 'crmUi', 'dialogService' |
f4f103fa | 5 | ]); // TODO ngSanitize, unsavedChanges |
030dce01 | 6 | |
7801d9b5 TO |
7 | // Time to wait before triggering AJAX update to recipients list |
8 | var RECIPIENTS_DEBOUNCE_MS = 100; | |
b73e0c53 | 9 | var RECIPIENTS_PREVIEW_LIMIT = 10000; |
7801d9b5 | 10 | |
88e9e883 | 11 | angular.module('crmMailing').config([ |
f4f103fa | 12 | '$routeProvider', |
030dce01 | 13 | function ($routeProvider) { |
96ac27bd | 14 | $routeProvider.when('/mailing', { |
030dce01 TO |
15 | template: '<div></div>', |
16 | controller: 'ListMailingsCtrl' | |
17 | }); | |
b7c3beb2 TO |
18 | |
19 | var editorPaths = { | |
ef5d18a1 TO |
20 | '': '~/crmMailing/edit.html', |
21 | '/unified': '~/crmMailing/edit-unified.html', | |
22 | '/unified2': '~/crmMailing/edit-unified2.html', | |
23 | '/wizard': '~/crmMailing/edit-wizard.html' | |
b7c3beb2 TO |
24 | }; |
25 | angular.forEach(editorPaths, function(editTemplate, pathSuffix) { | |
26 | $routeProvider.when('/mailing/new' + pathSuffix, { | |
27 | template: '<p>' + ts('Initializing...') + '</p>', | |
28 | controller: 'CreateMailingCtrl', | |
29 | resolve: { | |
30 | selectedMail: function(crmMailingMgr) { | |
31 | var m = crmMailingMgr.create(); | |
32 | return crmMailingMgr.save(m); | |
33 | } | |
f4f103fa | 34 | } |
b7c3beb2 TO |
35 | }); |
36 | $routeProvider.when('/mailing/:id' + pathSuffix, { | |
37 | templateUrl: editTemplate, | |
38 | controller: 'EditMailingCtrl', | |
39 | resolve: { | |
40 | selectedMail: function($route, crmMailingMgr) { | |
41 | return crmMailingMgr.get($route.current.params.id); | |
f2cdd789 TO |
42 | }, |
43 | attachments: function($route, CrmAttachments) { | |
44 | var attachments = new CrmAttachments(function () { | |
45 | return {entity_table: 'civicrm_mailing', entity_id: $route.current.params.id}; | |
46 | }); | |
47 | return attachments.load(); | |
b7c3beb2 | 48 | } |
f4f103fa | 49 | } |
b7c3beb2 | 50 | }); |
030dce01 TO |
51 | }); |
52 | } | |
53 | ]); | |
54 | ||
416abe87 | 55 | angular.module('crmMailing').controller('ListMailingsCtrl', ['crmLegacy', 'crmNavigator', function ListMailingsCtrl(crmLegacy, crmNavigator) { |
030dce01 TO |
56 | // We haven't implemented this in Angular, but some users may get clever |
57 | // about typing URLs, so we'll provide a redirect. | |
416abe87 PH |
58 | var new_url = crmLegacy.url('civicrm/mailing/browse/unscheduled', {reset: 1, scheduled: 'false'}); |
59 | crmNavigator.redirect(new_url); | |
60 | }]); | |
030dce01 | 61 | |
b7c3beb2 TO |
62 | angular.module('crmMailing').controller('CreateMailingCtrl', function EditMailingCtrl($scope, selectedMail, $location) { |
63 | // Transition URL "/mailing/new/foo" => "/mailing/123/foo" | |
64 | var parts = $location.path().split('/'); // e.g. "/mailing/new" or "/mailing/123/wizard" | |
65 | parts[2] = selectedMail.id; | |
66 | $location.path(parts.join('/')); | |
67 | $location.replace(); | |
68 | }); | |
69 | ||
e08a61f9 | 70 | angular.module('crmMailing').controller('EditMailingCtrl', function EditMailingCtrl($scope, selectedMail, $location, crmMailingMgr, crmStatus, attachments, crmMailingPreviewMgr, crmBlocker, CrmAutosaveCtrl, $timeout) { |
27e690c2 | 71 | $scope.mailing = selectedMail; |
f2cdd789 | 72 | $scope.attachments = attachments; |
27e690c2 TO |
73 | $scope.crmMailingConst = CRM.crmMailing; |
74 | ||
5d8901af | 75 | var ts = $scope.ts = CRM.ts(null); |
bdd3f781 | 76 | var block = $scope.block = crmBlocker(); |
27e690c2 | 77 | |
86c3a327 TO |
78 | $scope.isSubmitted = function isSubmitted() { |
79 | return _.size($scope.mailing.jobs) > 0; | |
80 | }; | |
81 | ||
58dfba8d TO |
82 | // @return Promise |
83 | $scope.previewMailing = function previewMailing(mailing, mode) { | |
84 | return crmMailingPreviewMgr.preview(mailing, mode); | |
85 | }; | |
86 | ||
87 | // @return Promise | |
88 | $scope.sendTest = function sendTest(mailing, attachments, recipient) { | |
89 | var savePromise = crmMailingMgr.save(mailing) | |
90 | .then(function () { | |
91 | return attachments.save(); | |
b7c3beb2 | 92 | }); |
bdd3f781 | 93 | return block(crmStatus({start: ts('Saving...'), success: ''}, savePromise) |
58dfba8d TO |
94 | .then(function () { |
95 | crmMailingPreviewMgr.sendTest(mailing, recipient); | |
bdd3f781 | 96 | })); |
58dfba8d TO |
97 | }; |
98 | ||
705c61e9 TO |
99 | // @return Promise |
100 | $scope.submit = function submit() { | |
c9ae63bb TO |
101 | if (block.check() || $scope.crmMailing.$invalid) { |
102 | return; | |
103 | } | |
104 | ||
db083bf0 | 105 | var promise = crmMailingMgr.save($scope.mailing) |
86c3a327 TO |
106 | .then(function () { |
107 | // pre-condition: the mailing exists *before* saving attachments to it | |
108 | return $scope.attachments.save(); | |
109 | }) | |
110 | .then(function () { | |
111 | return crmMailingMgr.submit($scope.mailing); | |
112 | }) | |
113 | .then(function () { | |
650a6ffc | 114 | $scope.leave('scheduled'); |
86c3a327 TO |
115 | }) |
116 | ; | |
bdd3f781 | 117 | return block(crmStatus({start: ts('Submitting...'), success: ts('Submitted')}, promise)); |
2d36e6bc | 118 | }; |
58dfba8d | 119 | |
705c61e9 TO |
120 | // @return Promise |
121 | $scope.save = function save() { | |
bdd3f781 | 122 | return block(crmStatus(null, |
db083bf0 TO |
123 | crmMailingMgr |
124 | .save($scope.mailing) | |
125 | .then(function () { | |
126 | // pre-condition: the mailing exists *before* saving attachments to it | |
127 | return $scope.attachments.save(); | |
128 | }) | |
bdd3f781 | 129 | )); |
2d36e6bc | 130 | }; |
58dfba8d | 131 | |
705c61e9 TO |
132 | // @return Promise |
133 | $scope.delete = function cancel() { | |
bdd3f781 | 134 | return block(crmStatus({start: ts('Deleting...'), success: ts('Deleted')}, |
f286acec | 135 | crmMailingMgr.delete($scope.mailing) |
b0797ac3 | 136 | .then(function () { |
650a6ffc | 137 | $scope.leave('unscheduled'); |
b0797ac3 | 138 | }) |
bdd3f781 | 139 | )); |
2d36e6bc | 140 | }; |
58dfba8d | 141 | |
b0797ac3 | 142 | // @param string listingScreen 'archive', 'scheduled', 'unscheduled' |
650a6ffc | 143 | $scope.leave = function leave(listingScreen) { |
b0797ac3 TO |
144 | switch (listingScreen) { |
145 | case 'archive': | |
146 | window.location = CRM.url('civicrm/mailing/browse/archived', { | |
147 | reset: 1 | |
148 | }); | |
149 | break; | |
150 | case 'scheduled': | |
151 | window.location = CRM.url('civicrm/mailing/browse/scheduled', { | |
152 | reset: 1, | |
153 | scheduled: 'true' | |
154 | }); | |
155 | break; | |
156 | case 'unscheduled': | |
8acf0123 | 157 | /* falls through */ |
b0797ac3 TO |
158 | default: |
159 | window.location = CRM.url('civicrm/mailing/browse/unscheduled', { | |
160 | reset: 1, | |
161 | scheduled: 'false' | |
162 | }); | |
163 | } | |
650a6ffc | 164 | }; |
e08a61f9 TO |
165 | |
166 | var myAutosave = new CrmAutosaveCtrl({ | |
167 | save: $scope.save, | |
168 | saveIf: function() { | |
169 | return true; | |
170 | }, | |
171 | model: function() { | |
172 | return [$scope.mailing, $scope.attachments.getAutosaveSignature()]; | |
173 | }, | |
174 | form: function() { | |
175 | return $scope.crmMailing; | |
176 | } | |
177 | }); | |
178 | $timeout(myAutosave.start); | |
179 | $scope.$on('$destroy', myAutosave.stop); | |
030dce01 TO |
180 | }); |
181 | ||
7801d9b5 TO |
182 | // Controller for the edit-recipients fields ( |
183 | // WISHLIST: Move most of this to a (cache-enabled) service | |
184 | // Scope members: | |
185 | // - [input] mailing: object | |
186 | // - [output] recipients: array of recipient records | |
08baf3ec | 187 | angular.module('crmMailing').controller('EditRecipCtrl', function EditRecipCtrl($scope, dialogService, crmApi, crmMailingMgr, $q, crmMetadata) { |
5d8901af | 188 | var ts = $scope.ts = CRM.ts(null); |
7801d9b5 TO |
189 | $scope.recipients = null; |
190 | $scope.getRecipientsEstimate = function () { | |
191 | var ts = $scope.ts; | |
8acf0123 | 192 | if ($scope.recipients === null) { |
7801d9b5 | 193 | return ts('(Estimating)'); |
f4f103fa | 194 | } |
8acf0123 | 195 | if ($scope.recipients.length === 0) { |
7801d9b5 | 196 | return ts('No recipients'); |
f4f103fa | 197 | } |
8acf0123 | 198 | if ($scope.recipients.length === 1) { |
7801d9b5 | 199 | return ts('~1 recipient'); |
f4f103fa TO |
200 | } |
201 | if (RECIPIENTS_PREVIEW_LIMIT > 0 && $scope.recipients.length >= RECIPIENTS_PREVIEW_LIMIT) { | |
b73e0c53 | 202 | return ts('>%1 recipients', {1: RECIPIENTS_PREVIEW_LIMIT}); |
f4f103fa | 203 | } |
7801d9b5 TO |
204 | return ts('~%1 recipients', {1: $scope.recipients.length}); |
205 | }; | |
f4f103fa | 206 | $scope.getIncludesAsString = function () { |
47bacc20 TO |
207 | var first = true; |
208 | var names = ''; | |
9cd4f489 | 209 | _.each($scope.mailing.recipients.groups.include, function (id) { |
f4f103fa TO |
210 | if (!first) { |
211 | names = names + ', '; | |
212 | } | |
213 | var group = _.where(CRM.crmMailing.groupNames, {id: '' + id}); | |
47bacc20 TO |
214 | names = names + group[0].title; |
215 | first = false; | |
216 | }); | |
9cd4f489 | 217 | _.each($scope.mailing.recipients.mailings.include, function (id) { |
f4f103fa TO |
218 | if (!first) { |
219 | names = names + ', '; | |
220 | } | |
221 | var oldMailing = _.where(CRM.crmMailing.civiMails, {id: '' + id}); | |
47bacc20 TO |
222 | names = names + oldMailing[0].name; |
223 | first = false; | |
224 | }); | |
225 | return names; | |
226 | }; | |
f4f103fa | 227 | $scope.getExcludesAsString = function () { |
47bacc20 TO |
228 | var first = true; |
229 | var names = ''; | |
9cd4f489 | 230 | _.each($scope.mailing.recipients.groups.exclude, function (id) { |
f4f103fa TO |
231 | if (!first) { |
232 | names = names + ', '; | |
233 | } | |
234 | var group = _.where(CRM.crmMailing.groupNames, {id: '' + id}); | |
47bacc20 TO |
235 | names = names + group[0].title; |
236 | first = false; | |
237 | }); | |
9cd4f489 | 238 | _.each($scope.mailing.recipients.mailings.exclude, function (id) { |
f4f103fa TO |
239 | if (!first) { |
240 | names = names + ', '; | |
241 | } | |
242 | var oldMailing = _.where(CRM.crmMailing.civiMails, {id: '' + id}); | |
47bacc20 TO |
243 | names = names + oldMailing[0].name; |
244 | first = false; | |
245 | }); | |
246 | return names; | |
247 | }; | |
248 | ||
7801d9b5 TO |
249 | // We monitor four fields -- use debounce so that changes across the |
250 | // four fields can settle-down before AJAX. | |
251 | var refreshRecipients = _.debounce(function () { | |
252 | $scope.$apply(function () { | |
253 | $scope.recipients = null; | |
8dfd5110 TO |
254 | crmMailingMgr.previewRecipients($scope.mailing, RECIPIENTS_PREVIEW_LIMIT).then(function (recipients) { |
255 | $scope.recipients = recipients; | |
b73e0c53 | 256 | }); |
7801d9b5 TO |
257 | }); |
258 | }, RECIPIENTS_DEBOUNCE_MS); | |
9cd4f489 TO |
259 | $scope.$watchCollection("mailing.recipients.groups.include", refreshRecipients); |
260 | $scope.$watchCollection("mailing.recipients.groups.exclude", refreshRecipients); | |
261 | $scope.$watchCollection("mailing.recipients.mailings.include", refreshRecipients); | |
262 | $scope.$watchCollection("mailing.recipients.mailings.exclude", refreshRecipients); | |
7801d9b5 | 263 | |
4dd19229 | 264 | $scope.previewRecipients = function previewRecipients() { |
7801d9b5 TO |
265 | var model = { |
266 | recipients: $scope.recipients | |
267 | }; | |
b1fc510d | 268 | var options = CRM.utils.adjustDialogDefaults({ |
7801d9b5 | 269 | autoOpen: false, |
7801d9b5 TO |
270 | title: ts('Preview (%1)', { |
271 | 1: $scope.getRecipientsEstimate() | |
52f515c6 | 272 | }) |
b1fc510d | 273 | }); |
ef5d18a1 | 274 | dialogService.open('recipDialog', '~/crmMailing/dialog/recipients.html', model, options); |
7801d9b5 | 275 | }; |
b8b2e316 TO |
276 | |
277 | // Open a dialog for editing the advanced recipient options. | |
278 | $scope.editOptions = function editOptions(mailing) { | |
b1fc510d | 279 | var options = CRM.utils.adjustDialogDefaults({ |
b8b2e316 | 280 | autoOpen: false, |
b8b2e316 | 281 | title: ts('Edit Options') |
b1fc510d | 282 | }); |
08baf3ec TO |
283 | $q.when(crmMetadata.getFields('Mailing')).then(function(fields) { |
284 | var model = { | |
285 | fields: fields, | |
286 | mailing: mailing | |
287 | }; | |
288 | dialogService.open('previewComponentDialog', '~/crmMailing/dialog/recipientOptions.html', model, options); | |
289 | }); | |
b8b2e316 | 290 | }; |
7801d9b5 TO |
291 | }); |
292 | ||
293 | // Controller for the "Preview Recipients" dialog | |
294 | // Note: Expects $scope.model to be an object with properties: | |
295 | // - recipients: array of contacts | |
88e9e883 | 296 | angular.module('crmMailing').controller('PreviewRecipCtrl', function ($scope) { |
5d8901af | 297 | $scope.ts = CRM.ts(null); |
7801d9b5 | 298 | }); |
493eb47a | 299 | |
493eb47a TO |
300 | // Controller for the "Preview Mailing" dialog |
301 | // Note: Expects $scope.model to be an object with properties: | |
302 | // - "subject" | |
303 | // - "body_html" | |
304 | // - "body_text" | |
870cbdbb | 305 | angular.module('crmMailing').controller('PreviewMailingDialogCtrl', function PreviewMailingDialogCtrl($scope) { |
5d8901af | 306 | $scope.ts = CRM.ts(null); |
493eb47a TO |
307 | }); |
308 | ||
b8b2e316 | 309 | // Controller for the "Recipients: Edit Options" dialog |
3cf58cc3 TO |
310 | // Note: Expects $scope.model to be an object with properties: |
311 | // - "mailing" (APIv3 mailing object) | |
312 | // - "fields" (list of fields) | |
b8b2e316 TO |
313 | angular.module('crmMailing').controller('EditRecipOptionsDialogCtrl', function EditRecipOptionsDialogCtrl($scope) { |
314 | $scope.ts = CRM.ts(null); | |
315 | }); | |
316 | ||
47bacc20 TO |
317 | // Controller for the "Preview Mailing Component" segment |
318 | // which displays header/footer/auto-responder | |
d376f33e | 319 | angular.module('crmMailing').controller('PreviewComponentCtrl', function PreviewComponentCtrl($scope, dialogService) { |
5d8901af | 320 | var ts = $scope.ts = CRM.ts(null); |
52f515c6 | 321 | |
47bacc20 | 322 | $scope.previewComponent = function previewComponent(title, componentId) { |
f4f103fa | 323 | var component = _.where(CRM.crmMailing.headerfooterList, {id: "" + componentId}); |
47bacc20 TO |
324 | if (!component || !component[0]) { |
325 | CRM.alert(ts('Invalid component ID (%1)', { | |
326 | 1: componentId | |
327 | })); | |
328 | return; | |
329 | } | |
b1fc510d | 330 | var options = CRM.utils.adjustDialogDefaults({ |
47bacc20 | 331 | autoOpen: false, |
47bacc20 | 332 | title: title // component[0].name |
b1fc510d | 333 | }); |
ef5d18a1 | 334 | dialogService.open('previewComponentDialog', '~/crmMailing/dialog/previewComponent.html', component[0], options); |
47bacc20 TO |
335 | }; |
336 | }); | |
337 | ||
d376f33e | 338 | // Controller for the "Preview Mailing Component" dialog |
47bacc20 TO |
339 | // Note: Expects $scope.model to be an object with properties: |
340 | // - "name" | |
341 | // - "subject" | |
342 | // - "body_html" | |
343 | // - "body_text" | |
d376f33e | 344 | angular.module('crmMailing').controller('PreviewComponentDialogCtrl', function PreviewComponentDialogCtrl($scope) { |
5d8901af | 345 | $scope.ts = CRM.ts(null); |
47bacc20 TO |
346 | }); |
347 | ||
744bebee | 348 | // Controller for the in-place msg-template management |
870cbdbb | 349 | angular.module('crmMailing').controller('MsgTemplateCtrl', function MsgTemplateCtrl($scope, crmMsgTemplates, dialogService) { |
5d8901af | 350 | var ts = $scope.ts = CRM.ts(null); |
744bebee TO |
351 | $scope.crmMsgTemplates = crmMsgTemplates; |
352 | ||
353 | // @return Promise MessageTemplate (per APIv3) | |
74263d6b | 354 | $scope.saveTemplate = function saveTemplate(mailing) { |
744bebee | 355 | var model = { |
74263d6b | 356 | selected_id: mailing.msg_template_id, |
744bebee TO |
357 | tpl: { |
358 | msg_title: '', | |
74263d6b TO |
359 | msg_subject: mailing.subject, |
360 | msg_text: mailing.body_text, | |
361 | msg_html: mailing.body_html | |
744bebee TO |
362 | } |
363 | }; | |
b1fc510d | 364 | var options = CRM.utils.adjustDialogDefaults({ |
744bebee | 365 | autoOpen: false, |
744bebee | 366 | title: ts('Save Template') |
b1fc510d | 367 | }); |
ef5d18a1 | 368 | return dialogService.open('saveTemplateDialog', '~/crmMailing/dialog/saveTemplate.html', model, options) |
f4f103fa | 369 | .then(function (item) { |
74263d6b | 370 | mailing.msg_template_id = item.id; |
744bebee TO |
371 | return item; |
372 | }); | |
373 | }; | |
374 | ||
375 | // @param int id | |
376 | // @return Promise | |
74263d6b | 377 | $scope.loadTemplate = function loadTemplate(mailing, id) { |
744bebee | 378 | return crmMsgTemplates.get(id).then(function (tpl) { |
74263d6b TO |
379 | mailing.subject = tpl.msg_subject; |
380 | mailing.body_text = tpl.msg_text; | |
381 | mailing.body_html = tpl.msg_html; | |
744bebee TO |
382 | }); |
383 | }; | |
384 | }); | |
385 | ||
386 | // Controller for the "Save Message Template" dialog | |
387 | // Scope members: | |
388 | // - [input] "model": Object | |
389 | // - "selected_id": int | |
390 | // - "tpl": Object | |
391 | // - "msg_subject": string | |
392 | // - "msg_text": string | |
393 | // - "msg_html": string | |
88e9e883 | 394 | angular.module('crmMailing').controller('SaveMsgTemplateDialogCtrl', function SaveMsgTemplateDialogCtrl($scope, crmMsgTemplates, dialogService) { |
5d8901af | 395 | var ts = $scope.ts = CRM.ts(null); |
744bebee TO |
396 | $scope.saveOpt = {mode: '', newTitle: ''}; |
397 | $scope.selected = null; | |
398 | ||
399 | $scope.save = function save() { | |
400 | var tpl = _.extend({}, $scope.model.tpl); | |
401 | switch ($scope.saveOpt.mode) { | |
402 | case 'add': | |
403 | tpl.msg_title = $scope.saveOpt.newTitle; | |
404 | break; | |
405 | case 'update': | |
406 | tpl.id = $scope.selected.id; | |
407 | tpl.msg_title = $scope.selected.msg_title; | |
408 | break; | |
409 | default: | |
410 | throw 'SaveMsgTemplateDialogCtrl: Unrecognized mode: ' + $scope.saveOpt.mode; | |
411 | } | |
412 | return crmMsgTemplates.save(tpl) | |
413 | .then(function (item) { | |
414 | CRM.status(ts('Saved')); | |
415 | return item; | |
416 | }); | |
417 | }; | |
418 | ||
419 | function scopeApply(f) { | |
420 | return function () { | |
421 | var args = arguments; | |
422 | $scope.$apply(function () { | |
423 | f.apply(args); | |
424 | }); | |
425 | }; | |
426 | } | |
427 | ||
428 | function init() { | |
429 | crmMsgTemplates.get($scope.model.selected_id).then( | |
430 | function (tpl) { | |
431 | $scope.saveOpt.mode = 'update'; | |
432 | $scope.selected = tpl; | |
433 | }, | |
434 | function () { | |
435 | $scope.saveOpt.mode = 'add'; | |
436 | $scope.selected = null; | |
437 | } | |
438 | ); | |
439 | // When using dialogService with a button bar, the major button actions | |
440 | // need to be registered with the dialog widget (and not embedded in | |
441 | // the body of the dialog). | |
269d44f5 CW |
442 | var buttons = [ |
443 | { | |
444 | text: ts('Save'), | |
445 | icons: {primary: 'ui-icon-check'}, | |
446 | click: function () { | |
447 | $scope.save().then(function (item) { | |
448 | dialogService.close('saveTemplateDialog', item); | |
449 | }); | |
450 | } | |
451 | }, | |
452 | { | |
453 | text: ts('Cancel'), | |
454 | icons: {primary: 'ui-icon-close'}, | |
455 | click: function () { | |
456 | dialogService.cancel('saveTemplateDialog'); | |
457 | } | |
458 | } | |
459 | ]; | |
744bebee TO |
460 | dialogService.setButtons('saveTemplateDialog', buttons); |
461 | } | |
f4f103fa | 462 | |
744bebee TO |
463 | setTimeout(scopeApply(init), 0); |
464 | }); | |
2d06b3b6 | 465 | |
87391d86 TO |
466 | angular.module('crmMailing').controller('EmailAddrCtrl', function EmailAddrCtrl($scope, crmFromAddresses, crmUiAlert) { |
467 | var ts = CRM.ts(null); | |
468 | function changeAlert(winnerField, loserField) { | |
469 | crmUiAlert({ | |
470 | title: ts('Conflict'), | |
471 | text: ts('The "%1" option conflicts with the "%2" option. The "%2" option has been disabled.', { | |
472 | 1: winnerField, | |
473 | 2: loserField | |
474 | }) | |
475 | }); | |
476 | } | |
477 | ||
0a993c89 | 478 | $scope.crmFromAddresses = crmFromAddresses; |
87391d86 TO |
479 | $scope.checkReplyToChange = function checkReplyToChange(mailing) { |
480 | if (!_.isEmpty(mailing.replyto_email) && mailing.override_verp == '0') { | |
481 | mailing.override_verp = '1'; | |
16f12592 | 482 | changeAlert(ts('Reply-To'), ts('Track Replies')); |
87391d86 TO |
483 | } |
484 | }; | |
485 | $scope.checkVerpChange = function checkVerpChange(mailing) { | |
486 | if (!_.isEmpty(mailing.replyto_email) && mailing.override_verp == '0') { | |
487 | mailing.replyto_email = ''; | |
488 | changeAlert(ts('Track Replies'), ts('Reply-To')); | |
489 | } | |
490 | }; | |
0a993c89 | 491 | }); |
21fb26b8 TO |
492 | |
493 | var lastEmailTokenAlert = null; | |
89f476c4 | 494 | angular.module('crmMailing').controller('EmailBodyCtrl', function EmailBodyCtrl($scope, crmMailingMgr, crmUiAlert, $timeout) { |
21fb26b8 TO |
495 | var ts = CRM.ts(null); |
496 | ||
89f476c4 TO |
497 | // ex: if (!hasAllTokens(myMailing, 'body_text)) alert('Oh noes!'); |
498 | $scope.hasAllTokens = function hasAllTokens(mailing, field) { | |
21fb26b8 TO |
499 | return _.isEmpty(crmMailingMgr.findMissingTokens(mailing, field)); |
500 | }; | |
501 | ||
89f476c4 TO |
502 | // ex: checkTokens(myMailing, 'body_text', 'insert:body_text') |
503 | // ex: checkTokens(myMailing, '*') | |
504 | $scope.checkTokens = function checkTokens(mailing, field, insertEvent) { | |
21fb26b8 TO |
505 | if (lastEmailTokenAlert) { |
506 | lastEmailTokenAlert.close(); | |
507 | } | |
89f476c4 TO |
508 | var missing, insertable; |
509 | if (field == '*') { | |
510 | insertable = false; | |
511 | missing = angular.extend({}, | |
512 | crmMailingMgr.findMissingTokens(mailing, 'body_html'), | |
513 | crmMailingMgr.findMissingTokens(mailing, 'body_text') | |
514 | ); | |
515 | } else { | |
516 | insertable = !_.isEmpty(insertEvent); | |
517 | missing = crmMailingMgr.findMissingTokens(mailing, field); | |
518 | } | |
519 | if (!_.isEmpty(missing)) { | |
520 | lastEmailTokenAlert = crmUiAlert({ | |
521 | type: 'error', | |
522 | title: ts('Required tokens'), | |
523 | templateUrl: '~/crmMailing/dialog/tokenAlert.html', | |
524 | scope: angular.extend($scope.$new(), { | |
525 | insertable: insertable, | |
526 | insertToken: function(token) { | |
527 | $timeout(function(){ | |
528 | $scope.$broadcast(insertEvent, '{' + token + '}'); | |
529 | $timeout(function(){ | |
530 | checkTokens(mailing, field, insertEvent); | |
531 | }); | |
532 | }); | |
533 | }, | |
534 | missing: missing | |
535 | }) | |
21fb26b8 | 536 | }); |
21fb26b8 | 537 | } |
d03e0d13 | 538 | }; |
21fb26b8 | 539 | }); |
030dce01 | 540 | })(angular, CRM.$, CRM._); |