Merge pull request #4893 from colemanw/INFRA-132
[civicrm-core.git] / CRM / Event / Form / Registration / AdditionalParticipant.php
1 <?php
2 /*
3 +--------------------------------------------------------------------+
4 | CiviCRM version 4.6 |
5 +--------------------------------------------------------------------+
6 | Copyright CiviCRM LLC (c) 2004-2014 |
7 +--------------------------------------------------------------------+
8 | This file is a part of CiviCRM. |
9 | |
10 | CiviCRM is free software; you can copy, modify, and distribute it |
11 | under the terms of the GNU Affero General Public License |
12 | Version 3, 19 November 2007 and the CiviCRM Licensing Exception. |
13 | |
14 | CiviCRM is distributed in the hope that it will be useful, but |
15 | WITHOUT ANY WARRANTY; without even the implied warranty of |
16 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
17 | See the GNU Affero General Public License for more details. |
18 | |
19 | You should have received a copy of the GNU Affero General Public |
20 | License and the CiviCRM Licensing Exception along |
21 | with this program; if not, contact CiviCRM LLC |
22 | at info[AT]civicrm[DOT]org. If you have questions about the |
23 | GNU Affero General Public License or the licensing of CiviCRM, |
24 | see the CiviCRM license FAQ at http://civicrm.org/licensing |
25 +--------------------------------------------------------------------+
26 */
27
28 /**
29 *
30 *
31 * @package CRM
32 * @copyright CiviCRM LLC (c) 2004-2014
33 * $Id$
34 *
35 */
36
37 /**
38 * This class generates form components for processing Event
39 *
40 */
41 class CRM_Event_Form_Registration_AdditionalParticipant extends CRM_Event_Form_Registration {
42
43 /**
44 * The defaults involved in this page
45 */
46 public $_defaults = array();
47
48 /**
49 * Pre-registered additional participant id.
50 */
51 public $additionalParticipantId = NULL;
52
53 /**
54 * Set variables up before form is built
55 *
56 * @return void
57 */
58 public function preProcess() {
59 parent::preProcess();
60
61 $participantNo = substr($this->_name, 12);
62
63 //lets process in-queue participants.
64 if ($this->_participantId && $this->_additionalParticipantIds) {
65 $this->_additionalParticipantId = CRM_Utils_Array::value($participantNo, $this->_additionalParticipantIds);
66 }
67
68 $participantCnt = $participantNo + 1;
69 $this->assign('formId', $participantNo);
70 $this->_params = array();
71 $this->_params = $this->get('params');
72
73 $participantTot = $this->_params[0]['additional_participants'] + 1;
74 $skipCount = count(array_keys($this->_params, "skip"));
75 if ($skipCount) {
76 $this->assign('skipCount', $skipCount);
77 }
78 CRM_Utils_System::setTitle(ts('Register Participant %1 of %2', array(1 => $participantCnt, 2 => $participantTot)));
79
80 //CRM-4320, hack to check last participant.
81 $this->_lastParticipant = FALSE;
82 if ($participantTot == $participantCnt) {
83 $this->_lastParticipant = TRUE;
84 }
85 $this->assign('lastParticipant', $this->_lastParticipant);
86 }
87
88 /**
89 * Set default values for the form. For edit/view mode
90 * the default values are retrieved from the database
91 *
92 *
93 * @return void
94 */
95 public function setDefaultValues() {
96 $defaults = $unsetSubmittedOptions = array();
97 $discountId = NULL;
98 //fix for CRM-3088, default value for discount set.
99 if (!empty($this->_values['discount'])) {
100 $discountId = CRM_Core_BAO_Discount::findSet($this->_eventId, 'civicrm_event');
101 if ($discountId && !empty($this->_values['event']['default_discount_fee_id'])) {
102 $discountKey = CRM_Core_DAO::getFieldValue("CRM_Core_DAO_OptionValue", $this->_values['event']['default_discount_fee_id'], 'weight', 'id'
103 );
104 $defaults['amount'] = key(array_slice($this->_values['discount'][$discountId], $discountKey - 1, $discountKey, TRUE));
105 }
106 }
107 if ($this->_priceSetId) {
108 foreach ($this->_feeBlock as $key => $val) {
109 if (empty($val['options'])) {
110 continue;
111 }
112
113 $optionsFull = CRM_Utils_Array::value('option_full_ids', $val, array());
114 foreach ($val['options'] as $keys => $values) {
115 if ($values['is_default'] && !in_array($keys, $optionsFull)) {
116 if ($val['html_type'] == 'CheckBox') {
117 $defaults["price_{$key}"][$keys] = 1;
118 }
119 else {
120 $defaults["price_{$key}"] = $keys;
121 }
122 }
123 }
124 if (!empty($optionsFull)) {
125 $unsetSubmittedOptions[$val['id']] = $optionsFull;
126 }
127 }
128 }
129
130 //CRM-4320, setdefault additional participant values.
131 if ($this->_allowConfirmation && $this->_additionalParticipantId) {
132 //hack to get set default from eventFees.php
133 $this->_discountId = $discountId;
134 $this->_pId = $this->_additionalParticipantId;
135 $this->_contactId = CRM_Core_DAO::getFieldValue('CRM_Event_DAO_Participant', $this->_additionalParticipantId, 'contact_id');
136 $participantDefaults = CRM_Event_Form_EventFees::setDefaultValues($this);
137 $participantDefaults = array_merge($this->_defaults, $participantDefaults);
138 // use primary email address if billing email address is empty
139 if (empty($this->_defaults["email-{$this->_bltID}"]) &&
140 !empty($this->_defaults["email-Primary"])
141 ) {
142 $participantDefaults["email-{$this->_bltID}"] = $this->_defaults["email-Primary"];
143 }
144 $defaults = array_merge($defaults, $participantDefaults);
145 }
146
147 $defaults = array_merge($this->_defaults, $defaults);
148
149 //reset values for all options those are full.
150 if (!empty($unsetSubmittedOptions) && empty($_POST)) {
151 $this->resetElementValue($unsetSubmittedOptions);
152 }
153
154 //load default campaign from page.
155 if (array_key_exists('participant_campaign_id', $this->_fields)) {
156 $defaults['participant_campaign_id'] = CRM_Utils_Array::value('campaign_id', $this->_values['event']);
157 }
158
159 return $defaults;
160 }
161
162 /**
163 * Build the form object
164 *
165 * @return void
166 */
167 public function buildQuickForm() {
168 $config = CRM_Core_Config::singleton();
169 $button = substr($this->controller->getButtonName(), -4);
170
171 $this->add('hidden', 'scriptFee', NULL);
172 $this->add('hidden', 'scriptArray', NULL);
173
174 if ($this->_values['event']['is_monetary']) {
175 CRM_Event_Form_Registration_Register::buildAmount($this);
176 }
177 $first_name = $last_name = NULL;
178 $pre = $post = array();
179 foreach (array(
180 'pre', 'post') as $keys) {
181 if (isset($this->_values['additional_custom_' . $keys . '_id'])) {
182 $this->buildCustom($this->_values['additional_custom_' . $keys . '_id'], 'additionalCustom' . ucfirst($keys), TRUE);
183 $$keys = CRM_Core_BAO_UFGroup::getFields($this->_values['additional_custom_' . $keys . '_id']);
184 }
185 foreach (array(
186 'first_name', 'last_name') as $name) {
187 if (array_key_exists($name, $$keys) &&
188 CRM_Utils_Array::value('is_required', CRM_Utils_Array::value($name, $$keys))
189 ) {
190 $$name = 1;
191 }
192 }
193 }
194
195 $required = ($button == 'skip' ||
196 $this->_values['event']['allow_same_participant_emails'] == 1 &&
197 ($first_name && $last_name)
198 ) ? FALSE : TRUE;
199
200 //add buttons
201 $js = NULL;
202 if ($this->isLastParticipant(TRUE) && empty($this->_values['event']['is_monetary'])) {
203 $js = array('onclick' => "return submitOnce(this,'" . $this->_name . "','" . ts('Processing') . "');");
204 }
205
206 //handle case where user might sart with waiting by group
207 //registration and skip some people and now group fit to
208 //become registered so need to take payment from user.
209 //this case only occurs at dynamic waiting status, CRM-4320
210 $statusMessage = NULL;
211 $allowToProceed = TRUE;
212 $includeSkipButton = TRUE;
213 $this->_resetAllowWaitlist = FALSE;
214
215 $pricesetFieldsCount = CRM_Price_BAO_PriceSet::getPricesetCount($this->_priceSetId);
216
217 if ($this->_lastParticipant || $pricesetFieldsCount) {
218 //get the participant total.
219 $processedCnt = self::getParticipantCount($this, $this->_params, TRUE);
220 }
221
222 if (!$this->_allowConfirmation && !empty($this->_params[0]['bypass_payment']) &&
223 $this->_lastParticipant
224 ) {
225
226 //get the event spaces.
227 $spaces = $this->_availableRegistrations;
228
229 $currentPageMaxCount = 1;
230 if ($pricesetFieldsCount) {
231 $currentPageMaxCount = $pricesetFieldsCount;
232 }
233
234 //we might did reset allow waiting in case of dynamic calculation
235 if (!empty($this->_params[0]['bypass_payment']) &&
236 is_numeric($spaces) &&
237 $processedCnt > $spaces
238 ) {
239 $this->_allowWaitlist = TRUE;
240 $this->set('allowWaitlist', TRUE);
241 }
242
243 //lets allow to become a part of runtime waiting list, if primary selected pay later.
244 $realPayLater = FALSE;
245 if (!empty($this->_values['event']['is_monetary']) && !empty($this->_values['event']['is_pay_later'])) {
246 $realPayLater = CRM_Utils_Array::value('is_pay_later', $this->_params[0]);
247 }
248
249 //truly spaces are greater than required.
250 if (is_numeric($spaces) && $spaces >= ($processedCnt + $currentPageMaxCount)) {
251 if (CRM_Utils_Array::value('amount', $this->_params[0], 0) == 0 || $this->_requireApproval) {
252 $this->_allowWaitlist = FALSE;
253 $this->set('allowWaitlist', $this->_allowWaitlist);
254 if ($this->_requireApproval) {
255 $statusMessage = ts("It looks like you are now registering a group of %1 participants. The event has %2 available spaces (you will not be wait listed). Registration for this event requires approval. You will receive an email once your registration has been reviewed.", array(1 => ++$processedCnt, 2 => $spaces));
256 }
257 else {
258 $statusMessage = ts("It looks like you are now registering a group of %1 participants. The event has %2 available spaces (you will not be wait listed).", array(1 => ++$processedCnt, 2 => $spaces));
259 }
260 }
261 else {
262 $statusMessage = ts("It looks like you are now registering a group of %1 participants. The event has %2 available spaces (you will not be wait listed). Please go back to the main registration page and reduce the number of additional people. You will also need to complete payment information.", array(1 => ++$processedCnt, 2 => $spaces));
263 $allowToProceed = FALSE;
264 }
265 CRM_Core_Session::setStatus($statusMessage, ts('Registration Error'), 'error');
266 }
267 elseif ($processedCnt == $spaces) {
268 if (CRM_Utils_Array::value('amount', $this->_params[0], 0) == 0
269 || $realPayLater || $this->_requireApproval
270 ) {
271 $this->_resetAllowWaitlist = TRUE;
272 if ($this->_requireApproval) {
273 $statusMessage = ts("If you skip this participant there will be enough spaces in the event for your group (you will not be wait listed). Registration for this event requires approval. You will receive an email once your registration has been reviewed.");
274 }
275 else {
276 $statusMessage = ts("If you skip this participant there will be enough spaces in the event for your group (you will not be wait listed).");
277 }
278 }
279 else {
280 //hey there is enough space and we require payment.
281 $statusMessage = ts("If you skip this participant there will be enough spaces in the event for your group (you will not be wait listed). Please go back to the main registration page and reduce the number of additional people. You will also need to complete payment information.");
282 $includeSkipButton = FALSE;
283 }
284 }
285 }
286
287 // for priceset with count
288 if ($pricesetFieldsCount && !empty($this->_values['event']['has_waitlist']) &&
289 !$this->_allowConfirmation
290 ) {
291
292 if ($this->_isEventFull) {
293 $statusMessage = ts('This event is currently full. You are registering for the waiting list. You will be notified if spaces become available.');
294 }
295 elseif ($this->_allowWaitlist ||
296 (!$this->_allowWaitlist && ($processedCnt + $pricesetFieldsCount) > $this->_availableRegistrations)
297 ) {
298
299 $waitingMsg = ts('It looks like you are registering more participants then there are spaces available. All participants will be added to the waiting list. You will be notified if spaces become available.');
300 $confirmedMsg = ts('It looks like there are enough spaces in this event for your group (you will not be wait listed).');
301 if ($this->_requireApproval) {
302 $waitingMsg = ts('It looks like you are now registering a group of %1 participants. The event has %2 available spaces (you will not be wait listed). Registration for this event requires approval. You will receive an email once your registration has been reviewed.');
303 $confirmedMsg = ts('It looks there are enough spaces in this event for your group (you will not be wait listed). Registration for this event requires approval. You will receive an email once your registration has been reviewed.');
304 }
305
306 $this->assign('waitingMsg', $waitingMsg);
307 $this->assign('confirmedMsg', $confirmedMsg);
308
309 $this->assign('availableRegistrations', $this->_availableRegistrations);
310 $this->assign('currentParticipantCount', $processedCnt);
311 $this->assign('allowGroupOnWaitlist', TRUE);
312
313 $paymentBypassed = NULL;
314 if (!empty($this->_params[0]['bypass_payment']) &&
315 !$this->_allowWaitlist &&
316 !$realPayLater &&
317 !$this->_requireApproval &&
318 !(CRM_Utils_Array::value('amount', $this->_params[0], 0) == 0)
319 ) {
320 $paymentBypassed = ts('Please go back to the main registration page, to complete payment information.');
321 }
322 $this->assign('paymentBypassed', $paymentBypassed);
323 }
324 }
325
326 $this->assign('statusMessage', $statusMessage);
327
328 $buttons = array(
329 array(
330 'type' => 'back',
331 'name' => ts('Go Back'),
332 'spacing' => '&nbsp;&nbsp;&nbsp;&nbsp',
333 ),
334 );
335
336 //CRM-4320
337 if ($allowToProceed) {
338 $buttons = array_merge($buttons, array(
339 array(
340 'type' => 'next',
341 'name' => ts('Continue'),
342 'spacing' => '&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;',
343 'isDefault' => TRUE,
344 'js' => $js,
345 ),
346 )
347 );
348 if ($includeSkipButton) {
349 $buttons = array_merge($buttons, array(
350 array(
351 'type' => 'next',
352 'name' => ts('Skip Participant'),
353 'subName' => 'skip',
354 'icon' => 'seek-next',
355 ))
356 );
357 }
358 }
359 $this->addButtons($buttons);
360 $this->addFormRule(array('CRM_Event_Form_Registration_AdditionalParticipant', 'formRule'), $this);
361 }
362
363 /**
364 * Global form rule
365 *
366 * @param array $fields
367 * The input form values.
368 * @param array $files
369 * The uploaded files if any.
370 * @param $self
371 *
372 *
373 * @return true if no errors, else array of errors
374 * @static
375 */
376 public static function formRule($fields, $files, $self) {
377 $errors = array();
378 //get the button name.
379 $button = substr($self->controller->getButtonName(), -4);
380
381 $realPayLater = FALSE;
382 if (!empty($self->_values['event']['is_monetary']) && !empty($self->_values['event']['is_pay_later'])) {
383 $realPayLater = CRM_Utils_Array::value('is_pay_later', $self->_params[0]);
384 }
385
386 if ($button != 'skip') {
387 //Check that either an email or firstname+lastname is included in the form(CRM-9587)
388 CRM_Event_Form_Registration_Register::checkProfileComplete($fields, $errors, $self->_eventId);
389
390 //Additional Participant can also register for an event only once
391 $isRegistered = CRM_Event_Form_Registration_Register::checkRegistration($fields, $self, TRUE);
392 if ($isRegistered) {
393 if ($self->_values['event']['allow_same_participant_emails']) {
394 $errors['_qf_default'] = ts('A person is already registered for this event.');
395 }
396 else {
397 $errors["email-{$self->_bltID}"] = ts('A person with this email address is already registered for this event.');
398 }
399 }
400
401 //get the complete params.
402 $params = $self->get('params');
403
404 //take the participant instance.
405 $addParticipantNum = substr($self->_name, 12);
406
407 if (is_array($params)) {
408 foreach ($params as $key => $value) {
409 if ($key != $addParticipantNum) {
410 if (!$self->_values['event']['allow_same_participant_emails']) {
411 //collect all email fields
412 $existingEmails = array();
413 $additionalParticipantEmails = array();
414 if (is_array($value)) {
415 foreach ($value as $key => $val) {
416 if (substr($key, 0, 6) == 'email-' && $val) {
417 $existingEmails[] = $val;
418 }
419 }
420 }
421 foreach ($fields as $key => $val) {
422 if (substr($key, 0, 6) == 'email-' && $val) {
423 $additionalParticipantEmails[] = $val;
424 $mailKey = $key;
425 }
426 }
427 //check if any emails are common to both arrays
428 if (count(array_intersect($existingEmails, $additionalParticipantEmails))) {
429 $errors[$mailKey] = ts('The email address must be unique for each participant.');
430 break;
431 }
432 }
433 else {
434 // check with first_name and last_name for additional participants
435 if (!empty($value['first_name']) && ($value['first_name'] == CRM_Utils_Array::value('first_name', $fields)) &&
436 (CRM_Utils_Array::value('last_name', $value) == CRM_Utils_Array::value('last_name', $fields))
437 ) {
438 $errors['first_name'] = ts('The first name and last name must be unique for each participant.');
439 break;
440 }
441 }
442 }
443 }
444 }
445
446 //check for atleast one pricefields should be selected
447 if (!empty($fields['priceSetId'])) {
448 $allParticipantParams = $params;
449
450 //format current participant params.
451 $allParticipantParams[$addParticipantNum] = self::formatPriceSetParams($self, $fields);
452 $totalParticipants = self::getParticipantCount($self, $allParticipantParams);
453
454 //validate price field params.
455 $priceSetErrors = self::validatePriceSet($self, $allParticipantParams);
456 $errors = array_merge($errors, CRM_Utils_Array::value($addParticipantNum, $priceSetErrors, array()));
457
458 if (!$self->_allowConfirmation &&
459 is_numeric($self->_availableRegistrations)
460 ) {
461 if (!empty($self->_params[0]['bypass_payment']) &&
462 !$self->_allowWaitlist &&
463 !$realPayLater &&
464 !$self->_requireApproval &&
465 !(CRM_Utils_Array::value('amount', $self->_params[0], 0) == 0) &&
466 $totalParticipants < $self->_availableRegistrations
467 ) {
468 $errors['_qf_default'] = ts("Your event registration will be confirmed. Please go back to the main registration page, to complete payment information.");
469 }
470 //check for availability of registrations.
471 if (!$self->_allowConfirmation && empty($self->_values['event']['has_waitlist']) &&
472 $totalParticipants > $self->_availableRegistrations
473 ) {
474 $errors['_qf_default'] = ts('It looks like event has only %2 seats available and you are trying to register %1 participants, so could you please select price options accordingly.', array(1 => $totalParticipants, 2 => $self->_availableRegistrations));
475 }
476 }
477 }
478 }
479
480 if ($button == 'skip' && $self->_lastParticipant && !empty($fields['priceSetId'])) {
481 $pricesetFieldsCount = CRM_Price_BAO_PriceSet::getPricesetCount($fields['priceSetId']);
482 if (($pricesetFieldsCount < 1) || $self->_allowConfirmation) {
483 return $errors;
484 }
485
486 if (!empty($self->_values['event']['has_waitlist']) && !empty($self->_params[0]['bypass_payment']) &&
487 !$self->_allowWaitlist &&
488 !$realPayLater &&
489 !$self->_requireApproval &&
490 !(CRM_Utils_Array::value('amount', $self->_params[0], 0) == 0)
491 ) {
492 $errors['_qf_default'] = ts("You are going to skip the last participant, your event registration will be confirmed. Please go back to the main registration page, to complete payment information.");
493 }
494 }
495
496 if ($button != 'skip' &&
497 $self->_values['event']['is_monetary'] &&
498 !isset($errors['_qf_default']) &&
499 !$self->validatePaymentValues($self, $fields)
500 ) {
501 $errors['_qf_default'] = ts("Your payment information looks incomplete. Please go back to the main registration page, to complete payment information.");
502 $self->set('forcePayement', TRUE);
503 }
504 elseif ($button == 'skip') {
505 $self->set('forcePayement', TRUE);
506 }
507
508 return $errors;
509 }
510
511 /**
512 * @param $self
513 * @param $fields
514 *
515 * @return bool
516 */
517 public function validatePaymentValues($self, $fields) {
518
519 if (!empty($self->_params[0]['bypass_payment']) ||
520 $self->_allowWaitlist ||
521 empty($self->_fields) ||
522 CRM_Utils_Array::value('amount', $self->_params[0]) > 0
523 ) {
524 return TRUE;
525 }
526
527 $validatePayement = FALSE;
528 if (!empty($fields['priceSetId'])) {
529 $lineItem = array();
530 CRM_Price_BAO_PriceSet::processAmount($self->_values['fee'], $fields, $lineItem);
531 if ($fields['amount'] > 0) {
532 $validatePayement = TRUE;
533 // $self->_forcePayement = true;
534 // return false;
535 }
536 }
537 elseif (!empty($fields['amount']) &&
538 (CRM_Utils_Array::value('value', $self->_values['fee'][$fields['amount']]) > 0)
539 ) {
540 $validatePayement = TRUE;
541 }
542
543 if (!$validatePayement) {
544 return TRUE;
545 }
546
547 $errors = array();
548
549 CRM_Core_Form::validateMandatoryFields($self->_fields, $fields, $errors);
550
551 // make sure that credit card number and cvv are valid
552 CRM_Core_Payment_Form::validateCreditCard($self->_params[0], $errors);
553
554 if ($errors) {
555 return FALSE;
556 }
557
558 foreach (CRM_Contact_BAO_Contact::$_greetingTypes as $greeting) {
559 if ($greetingType = CRM_Utils_Array::value($greeting, $self->_params[0])) {
560 $customizedValue = CRM_Core_OptionGroup::getValue($greeting, 'Customized', 'name');
561 if ($customizedValue == $greetingType && empty($self->_params[0][$greeting . '_custom'])) {
562 return FALSE;
563 }
564 }
565 }
566 }
567
568 /**
569 * Process the form submission
570 *
571 *
572 * @return void
573 */
574 public function postProcess() {
575 //get the button name.
576 $button = substr($this->controller->getButtonName(), -4);
577
578 //take the participant instance.
579 $addParticipantNum = substr($this->_name, 12);
580
581 //user submitted params.
582 $params = $this->controller->exportValues($this->_name);
583
584 if (!$this->_allowConfirmation) {
585 // check if the participant is already registered
586 $params['contact_id'] = CRM_Event_Form_Registration_Register::checkRegistration($params, $this, TRUE, TRUE);
587 }
588
589 //carry campaign to partcipants.
590 if (array_key_exists('participant_campaign_id', $params)) {
591 $params['campaign_id'] = $params['participant_campaign_id'];
592 }
593 else {
594 $params['campaign_id'] = CRM_Utils_Array::value('campaign_id', $this->_values['event']);
595 }
596
597 // if waiting is enabled
598 if (!$this->_allowConfirmation &&
599 is_numeric($this->_availableRegistrations)
600 ) {
601 $this->_allowWaitlist = FALSE;
602 //get the current page count.
603 $currentCount = self::getParticipantCount($this, $params);
604 if ($button == 'skip') {
605 $currentCount = 'skip';
606 }
607
608 //get the total count.
609 $previousCount = self::getParticipantCount($this, $this->_params, TRUE);
610 $totalParticipants = $previousCount;
611 if (is_numeric($currentCount)) {
612 $totalParticipants += $currentCount;
613 }
614 if (!empty($this->_values['event']['has_waitlist']) &&
615 $totalParticipants > $this->_availableRegistrations
616 ) {
617 $this->_allowWaitlist = TRUE;
618 }
619 $this->set('allowWaitlist', $this->_allowWaitlist);
620 $this->_lineItemParticipantsCount[$addParticipantNum] = $currentCount;
621 }
622
623 if ($button == 'skip') {
624 //hack for free/zero amount event.
625 if ($this->_resetAllowWaitlist) {
626 $this->_allowWaitlist = FALSE;
627 $this->set('allowWaitlist', FALSE);
628 if ($this->_requireApproval) {
629 $status = ts("You have skipped last participant and which result into event having enough spaces, but your registration require approval, Once your registration has been reviewed, you will receive an email with a link to a web page where you can complete the registration process.");
630 }
631 else {
632 $status = ts("You have skipped last participant and which result into event having enough spaces, hence your group become as register participants though you selected on wait list.");
633 }
634 CRM_Core_Session::setStatus($status);
635 }
636
637 $this->_params[$addParticipantNum] = 'skip';
638 if (isset($this->_lineItem)) {
639 $this->_lineItem[$addParticipantNum] = 'skip';
640 $this->_lineItemParticipantsCount[$addParticipantNum] = 'skip';
641 }
642 }
643 else {
644
645 $config = CRM_Core_Config::singleton();
646 $params['currencyID'] = $config->defaultCurrency;
647
648 if ($this->_values['event']['is_monetary']) {
649
650 //added for discount
651 $discountId = CRM_Core_BAO_Discount::findSet($this->_eventId, 'civicrm_event');
652
653 if (!empty($this->_values['discount'][$discountId])) {
654 $params['discount_id'] = $discountId;
655 $params['amount_level'] = $this->_values['discount'][$discountId][$params['amount']]['label'];
656 $params['amount'] = $this->_values['discount'][$discountId][$params['amount']]['value'];
657 }
658 elseif (empty($params['priceSetId'])) {
659 $params['amount_level'] = $this->_values['fee'][$params['amount']]['label'];
660 $params['amount'] = $this->_values['fee'][$params['amount']]['value'];
661 }
662 else {
663 $lineItem = array();
664 CRM_Price_BAO_PriceSet::processAmount($this->_values['fee'], $params, $lineItem);
665
666 //build the line item..
667 if (array_key_exists($addParticipantNum, $this->_lineItem)) {
668 $this->_lineItem[$addParticipantNum] = $lineItem;
669 }
670 else {
671 $this->_lineItem[] = $lineItem;
672 }
673 }
674 }
675
676 if (array_key_exists('participant_role', $params)) {
677 $params['participant_role_id'] = $params['participant_role'];
678 }
679
680 if (empty($params['participant_role_id']) && $this->_values['event']['default_role_id']) {
681 $params['participant_role_id'] = $this->_values['event']['default_role_id'];
682 }
683
684 if (!empty($this->_params[0]['is_pay_later'])) {
685 $params['is_pay_later'] = 1;
686 }
687
688 //carry additional participant id, contact id if pre-registered.
689 if ($this->_allowConfirmation && $this->_additionalParticipantId) {
690 $params['contact_id'] = $this->_contactId;
691 $params['participant_id'] = $this->_additionalParticipantId;
692 }
693
694 //build the params array.
695 if (array_key_exists($addParticipantNum, $this->_params)) {
696 $this->_params[$addParticipantNum] = $params;
697 }
698 else {
699 $this->_params[] = $params;
700 }
701 }
702
703 //finally set the params.
704 $this->set('params', $this->_params);
705 //set the line item.
706 if ($this->_lineItem) {
707 $this->set('lineItem', $this->_lineItem);
708 $this->set('lineItemParticipantsCount', $this->_lineItemParticipantsCount);
709 }
710
711 $participantNo = count($this->_params);
712 if ($button != 'skip') {
713 $statusMsg = ts('Registration information for participant %1 has been saved.', array(1 => $participantNo));
714 CRM_Core_Session::setStatus($statusMsg, ts('Registration Saved'), 'success');
715 }
716
717 // Check whether to process the registration now, calling processRegistration()
718 if (
719 !$this->_values['event']['is_confirm_enabled'] // CRM-11182 - Optional confirmation screen
720 && !$this->_values['event']['is_monetary']
721 && CRM_Utils_Array::value('additional_participants', $this->_params[0])
722 && $this->isLastParticipant()
723 ) {
724 CRM_Event_Form_Registration_Register::processRegistration($this->_params, NULL);
725 }
726 }
727
728 /**
729 * @param $additionalParticipant
730 *
731 * @return array
732 */
733 public static function &getPages($additionalParticipant) {
734 $details = array();
735 for ($i = 1; $i <= $additionalParticipant; $i++) {
736 $details["Participant_{$i}"] = array(
737 'className' => 'CRM_Event_Form_Registration_AdditionalParticipant',
738 'title' => "Register Additional Participant {$i}",
739 );
740 }
741 return $details;
742 }
743
744 /**
745 * Check whether call current participant is last one
746 *
747 * @param bool $isButtonJs
748 *
749 * @return boolean
750 * ture on success.
751 */
752 public function isLastParticipant($isButtonJs = FALSE) {
753 $participant = $isButtonJs ? $this->_params[0]['additional_participants'] : $this->_params[0]['additional_participants'] + 1;
754 if (count($this->_params) == $participant) {
755 return TRUE;
756 }
757 return FALSE;
758 }
759
760 /**
761 * Reset values for all options those are full.
762 *
763 **/
764 public function resetElementValue($optionFullIds = array()) {
765 if (!is_array($optionFullIds) ||
766 empty($optionFullIds) ||
767 !$this->isSubmitted()
768 ) {
769 return;
770 }
771
772 foreach ($optionFullIds as $fldId => $optIds) {
773 $name = "price_$fldId";
774 if (!$this->elementExists($name)) {
775 continue;
776 }
777
778 $element = $this->getElement($name);
779 $eleType = $element->getType();
780
781 $resetSubmitted = FALSE;
782 switch ($eleType) {
783 case 'text':
784 if ($element->isFrozen()) {
785 $element->setValue('');
786 $resetSubmitted = TRUE;
787 }
788 break;
789
790 case 'group':
791 if (is_array($element->_elements)) {
792 foreach ($element->_elements as $child) {
793 $childType = $child->getType();
794 $methodName = 'getName';
795 if ($childType) {
796 $methodName = 'getValue';
797 }
798 if (in_array($child->{$methodName}(), $optIds) && $child->isFrozen()) {
799 $resetSubmitted = TRUE;
800 $child->updateAttributes(array('checked' => NULL));
801 }
802 }
803 }
804 break;
805
806 case 'select':
807 $resetSubmitted = TRUE;
808 $element->_values = array();
809 break;
810 }
811
812 //finally unset values from submitted.
813 if ($resetSubmitted) {
814 $this->resetSubmittedValue($name, $optIds);
815 }
816 }
817 }
818
819 /**
820 * @param string $elementName
821 * @param array $optionIds
822 */
823 public function resetSubmittedValue($elementName, $optionIds = array()) {
824 if (empty($elementName) ||
825 !$this->elementExists($elementName) ||
826 !$this->getSubmitValue($elementName)
827 ) {
828 return;
829 }
830 foreach (array(
831 'constantValues', 'submitValues', 'defaultValues') as $val) {
832 $values = &$this->{"_$val"};
833 if (!is_array($values) || empty($values)) {
834 continue;
835 }
836 $eleVal = CRM_Utils_Array::value($elementName, $values);
837 if (empty($eleVal)) {
838 continue;
839 }
840 if (is_array($eleVal)) {
841 $found = FALSE;
842 foreach ($eleVal as $keyId => $ignore) {
843 if (in_array($keyId, $optionIds)) {
844 $found = TRUE;
845 unset($values[$elementName][$keyId]);
846 }
847 }
848 if ($found && empty($values[$elementName][$keyId])) {
849 $values[$elementName][$keyId] = NULL;
850 }
851 }
852 else {
853 $values[$elementName][$keyId] = NULL;
854 }
855 }
856 }
857 }