Merge pull request #5317 from sfe-ev/chainselect-missing-fields
[civicrm-core.git] / templates / CRM / Contact / Page / View / Summary.js
1 // http://civicrm.org/licensing
2 (function($, _) {
3 // FIXME: Much of this code is redundant with CRM.loadForm
4
5 var ajaxFormParams = {
6 dataType:'json',
7 beforeSubmit: function(arr, $form, options) {
8 $form.block();
9 },
10 beforeSerialize: function(form, options) {
11 // Copied from crm.ajax.js
12 if (window.CKEDITOR && window.CKEDITOR.instances) {
13 $.each(CKEDITOR.instances, function() {
14 this.updateElement && this.updateElement();
15 });
16 }
17 if (window.tinyMCE && tinyMCE.editors) {
18 $.each(tinyMCE.editors, function() {
19 this.save();
20 });
21 }
22 },
23 success: requestHandler,
24 error: errorHandler
25 };
26
27 function crmFormInline(o) {
28 var data = o.data('edit-params');
29 if (o.is('.crm-edit-ready .crm-inline-edit') && data) {
30 o.animate({height: '+=50px'}, 200);
31 data.snippet = 6;
32 data.reset = 1;
33 o.addClass('form');
34 $('.crm-edit-ready').removeClass('crm-edit-ready');
35 o.block();
36 $.getJSON(CRM.url('civicrm/ajax/inline', data))
37 .fail(errorHandler)
38 .done(function(response) {
39 o.unblock();
40 o.css('overflow', 'hidden').wrapInner('<div class="inline-edit-hidden-content" style="display:none" />').append(response.content);
41 // Smooth resizing
42 var newHeight = $('.crm-container-snippet', o).height();
43 var diff = newHeight - parseInt(o.css('height'), 10);
44 if (diff < 0) {
45 diff = 0 - diff;
46 }
47 o.animate({height: '' + newHeight + 'px'}, diff * 2, function() {
48 o.removeAttr('style');
49 });
50 $('form', o).validate(CRM.validate.params);
51 ajaxFormParams.data = data;
52 $('form', o).ajaxForm(ajaxFormParams);
53 o.trigger('crmLoad').trigger('crmFormLoad');
54 });
55 }
56 }
57
58 function reloadBlock(el) {
59 return $(el).each(function() {
60 var data = $(this).data('edit-params');
61 data.snippet = data.reset = 1;
62 data.class_name = data.class_name.replace('Form', 'Page');
63 data.type = 'page';
64 $(this).closest('.crm-summary-block').load(CRM.url('civicrm/ajax/inline', data), function() {$(this).trigger('crmLoad');});
65 });
66 }
67
68 function requestHandler(response) {
69 var o = $('div.crm-inline-edit.form');
70 $('form', o).ajaxFormUnbind();
71
72 if (response.status == 'success' || response.status == 'cancel') {
73 o.trigger('crmFormSuccess', [response]);
74 $('.crm-inline-edit-container').addClass('crm-edit-ready');
75 var data = o.data('edit-params');
76 var dependent = o.data('dependent-fields') || [];
77 // Clone the add-new link if replacing it, and queue the clone to be refreshed as a dependent block
78 if (o.hasClass('add-new') && response.addressId) {
79 data.aid = response.addressId;
80 var clone = o.closest('.crm-summary-block').clone();
81 o.data('edit-params', data);
82 $('form', clone).remove();
83 if (clone.hasClass('contactCardLeft')) {
84 clone.removeClass('contactCardLeft').addClass('contactCardRight');
85 }
86 else if (clone.hasClass('contactCardRight')) {
87 clone.removeClass('contactCardRight').addClass('contactCardLeft');
88 }
89 var cl = $('.crm-inline-edit', clone);
90 var clData = cl.data('edit-params');
91 var locNo = clData.locno++;
92 cl.attr('id', cl.attr('id').replace(locNo, clData.locno)).removeClass('form');
93 o.closest('.crm-summary-block').after(clone);
94 $.merge(dependent, $('.crm-inline-edit', clone));
95 }
96 $('a.ui-notify-close', '#crm-notification-container').click();
97 // Delete an address
98 if (o.hasClass('address') && !o.hasClass('add-new') && !response.addressId) {
99 o.parent().remove();
100 CRM.status(ts('Address Deleted'));
101 }
102 else {
103 // Reload this block plus all dependent blocks
104 var update = $.merge([o], dependent);
105 _.each(update, reloadBlock);
106 CRM.status(ts('Saved'));
107 }
108 // Update changelog tab and contact footer
109 if (response.changeLog && response.changeLog.count) {
110 CRM.tabHeader.updateCount('#tab_log', response.changeLog.count);
111 }
112 $("#crm-record-log").replaceWith(response.changeLog.markup);
113 // Refresh tab contents - Simple logging
114 if (!CRM.reloadChangeLogTab && $('#changeLog').closest('.ui-tabs-panel').data('civiCrmSnippet')) {
115 $('#changeLog').closest('.ui-tabs-panel').crmSnippet('destroy');
116 }
117 }
118 else {
119 // Handle formRule error
120 $('.crm-container-snippet', o).replaceWith(response.content);
121 $('form', o).validate(CRM.validate.params);
122 $('form', o).ajaxForm(ajaxFormParams);
123 o.trigger('crmFormError', [response]).trigger('crmFormLoad').trigger('crmLoad');
124 }
125 }
126
127 /**
128 * Configure optimistic locking mechanism for inplace editing
129 *
130 * options.ignoreLabel: string, text for a button
131 * options.reloadLabel: string, text for a button
132 */
133 $.fn.crmFormContactLock = function(options) {
134 var form = this;
135 // AFTER ERROR: Render any "Ignore" and "Restart" buttons
136 return this.on('crmFormError', function(event, obj, status) {
137 var o = $(event.target);
138 var data = o.data('edit-params');
139 var errorTag = o.find('.update_oplock_ts');
140 if (errorTag.length > 0) {
141 $('<span>')
142 .addClass('crm-lock-button')
143 .appendTo(errorTag);
144
145 var buttonContainer = o.find('.crm-lock-button');
146 $('<button>')
147 .addClass('crm-button')
148 .text(options.saveAnywayLabel)
149 .click(function() {
150 $(form).find('input[name=oplock_ts]').val(errorTag.attr('data:update_oplock_ts'));
151 errorTag.parent().hide();
152 $(this).closest('form').find('.crm-form-submit.default').first().click();
153 return false;
154 })
155 .appendTo(buttonContainer)
156 ;
157 $('<button>')
158 .addClass('crm-button')
159 .text(options.reloadLabel)
160 .click(function() {
161 window.location.reload();
162 return false;
163 })
164 .appendTo(buttonContainer)
165 ;
166 }
167 });
168 };
169
170 function errorHandler(response) {
171 CRM.alert(ts('Unable to reach the server. Please refresh this page in your browser and try again.'), ts('Network Error'), 'error');
172 $('.crm-inline-edit.form form').unblock();
173 }
174
175 $(function() {
176 // don't perform inline edit during print mode
177 if (CRM.summaryPrint.mode) {
178 $('div').removeClass('crm-inline-edit');
179 $('.crm-inline-block-content > div.crm-edit-help').remove();
180 $('div.crm-inline-block-content').removeAttr('title');
181 }
182 // Set page title
183 var oldName = 'CiviCRM';
184 var nameTitle = $('#crm-remove-title');
185 if (nameTitle.length > 0) {
186 oldName = nameTitle.text();
187 nameTitle.parent('h1').remove();
188 }
189 else {
190 $('h1').each(function() {
191 if ($(this).text() == oldName) {
192 $(this).remove();
193 }
194 });
195 }
196 function refreshTitle() {
197 var contactName = $('.crm-summary-display_name').text();
198 contactName = $.trim(contactName);
199 document.title = $('title').html().replace(oldName, contactName);
200 oldName = contactName;
201 }
202 $('#contactname-block').load(refreshTitle);
203 refreshTitle();
204
205 var clicking;
206 $('.crm-inline-edit-container')
207 .addClass('crm-edit-ready')
208 // Allow links inside edit blocks to be clicked without triggering edit
209 .on('mousedown', '.crm-inline-edit:not(.form) a, .crm-inline-edit:not(.form) .crm-accordion-header, .crm-inline-edit:not(.form) .collapsible-title', function(event) {
210 if (event.which == 1) {
211 event.stopPropagation();
212 return false;
213 }
214 })
215 // Respond to a click (not drag, not right-click) of crm-inline-edit blocks
216 .on('mousedown', '.crm-inline-edit:not(.form)', function(button) {
217 if (button.which == 1) {
218 clicking = this;
219 setTimeout(function() {clicking = null;}, 500);
220 }
221 })
222 .on('mouseup', '.crm-inline-edit:not(.form)', function(button) {
223 if (clicking === this && button.which == 1) {
224 crmFormInline($(this));
225 }
226 })
227 // Inline edit form cancel button
228 .on('click', '.crm-inline-edit :submit[name$=cancel]', function() {
229 var container = $(this).closest('.crm-inline-edit.form');
230 $('form', container).ajaxFormUnbind();
231 $('.inline-edit-hidden-content', container).nextAll().remove();
232 $('.inline-edit-hidden-content > *:first-child', container).unwrap();
233 container.removeClass('form');
234 $('.crm-inline-edit-container').addClass('crm-edit-ready');
235 $('a.ui-notify-close', '#crm-notification-container').click();
236 return false;
237 })
238 // Switch tabs when clicking tag link
239 .on('click', '#tagLink a', function() {
240 $('#tab_tag a').click();
241 return false;
242 })
243 // make sure only one is_primary radio is checked
244 .on('change', '[class$=is_primary] input', function() {
245 if ($(this).is(':checked')) {
246 $('[class$=is_primary] input', $(this).closest('form')).not(this).prop('checked', false);
247 }
248 })
249 // make sure only one builk_mail radio is checked
250 .on('change', '.crm-email-bulkmail input', function(){
251 if ($(this).is(':checked')) {
252 $('.crm-email-bulkmail input').not(this).prop('checked', false);
253 }
254 })
255 // handle delete link within blocks
256 .on('click', '.crm-delete-inline', function(e) {
257 var row = $(this).closest('tr');
258 var form = $(this).closest('form');
259 row.hide();
260 $('input', row).val('');
261 //if the primary is checked for deleted block
262 //unset and set first as primary
263 if ($('[class$=is_primary] input:checked', row).length > 0) {
264 $('[class$=is_primary] input', row).prop('checked', false);
265 $('[class$=is_primary] input:first', form).prop('checked', true );
266 }
267 $('.add-more-inline', form).show();
268 e.preventDefault();
269 })
270 // Delete an address
271 .on('click', '.crm-inline-edit.address .delete-button', function() {
272 var $block = $(this).closest('.crm-inline-edit.address');
273 CRM.confirm(function() {
274 CRM.api('address', 'delete', {id: $block.data('edit-params').aid}, {success:
275 function(data) {
276 CRM.status(ts('Address Deleted'));
277 $('.crm-inline-edit-container').addClass('crm-edit-ready');
278 $block.remove();
279 }
280 });
281 },
282 {
283 message: ts('Are you sure you want to delete this address?')
284 }
285 );
286 return false;
287 })
288 // add more and set focus to new row
289 .on('click', '.add-more-inline', function(e) {
290 var form = $(this).closest('form');
291 var row = $('tr[class="hiddenElement"]:first', form);
292 row.removeClass('hiddenElement');
293 $('input:focus', form).blur();
294 $('input:first', row).focus();
295 if ($('tr[class="hiddenElement"]').length < 1) {
296 $(this).hide();
297 }
298 e.preventDefault();
299 });
300 // Trigger cancel button on esc keypress
301 $(document).keydown(function(key) {
302 if (key.which == 27) {
303 $('.crm-inline-edit.form :submit[name$=cancel]').click();
304 }
305 });
306 $('#crm-container')
307 // Switch tabs when clicking log link
308 .on('click', '#crm-record-log a.crm-log-view', function() {
309 $('#tab_log a').click();
310 return false;
311 })
312 // Handle action links in popup
313 .on('click', '.crm-contact_actions-list a, .crm-contact_activities-list a', function(e) {
314 $('#crm-contact-actions-list').hide();
315 if ($(this).attr('href') === '#') {
316 var $tab = $('#tab_' + ($(this).data('tab') || 'summary'));
317 CRM.tabHeader.focus($tab);
318 e.preventDefault();
319 } else {
320 CRM.popup.call(this, e);
321 }
322 })
323 .on('crmPopupFormSuccess', '.crm-contact_actions-list a, .crm-contact_activities-list a', function() {
324 var $tab = $('#tab_' + ($(this).data('tab') || 'summary'));
325 CRM.tabHeader.resetTab($tab);
326 CRM.tabHeader.focus($tab);
327 });
328 $(document)
329 // Actions menu
330 .on('click', function(e) {
331 if ($(e.target).is('#crm-contact-actions-link, #crm-contact-actions-link *')) {
332 $('#crm-contact-actions-list').show();
333 return false;
334 }
335 $('#crm-contact-actions-list').hide();
336 })
337 .on('crmFormSuccess', function(e, data) {
338 // Reload changelog whenever an inline or popup form submits
339 CRM.reloadChangeLogTab && CRM.reloadChangeLogTab();
340 // Refresh dependent blocks
341 if (data && data.reloadBlocks) {
342 _.each(data.reloadBlocks, reloadBlock);
343 }
344 });
345 });
346 })(CRM.$, CRM._);