1<?php
2/*
3        +-----------------------------------------------------------------------------+
4        | ILIAS open source                                                           |
5        +-----------------------------------------------------------------------------+
6        | Copyright (c) 1998-2006 ILIAS open source, University of Cologne            |
7        |                                                                             |
8        | This program is free software; you can redistribute it and/or               |
9        | modify it under the terms of the GNU General Public License                 |
10        | as published by the Free Software Foundation; either version 2              |
11        | of the License, or (at your option) any later version.                      |
12        |                                                                             |
13        | This program is distributed in the hope that it will be useful,             |
14        | but WITHOUT ANY WARRANTY; without even the implied warranty of              |
15        | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the               |
16        | GNU General Public License for more details.                                |
17        |                                                                             |
18        | You should have received a copy of the GNU General Public License           |
19        | along with this program; if not, write to the Free Software                 |
20        | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA. |
21        +-----------------------------------------------------------------------------+
22*/
23
24include_once('Services/PrivacySecurity/classes/class.ilPrivacySettings.php');
25
26/**
27* Base class for Course and Group registration
28*
29* @author Stefan Meyer <smeyer.ilias@gmx.de>
30* @version $Id$
31*
32* @ingroup ServicesRegistration
33*/
34
35abstract class ilRegistrationGUI
36{
37    protected $privacy = null;
38
39    protected $container = null;
40    protected $ref_id;
41    protected $obj_id;
42
43    /**
44     * @var ilParticipants
45     */
46    protected $participants;
47    protected $waiting_list = null;
48    protected $form;
49
50    protected $registration_possible = true;
51    protected $join_error = '';
52
53
54    protected $tpl;
55    protected $lng;
56    protected $ctrl;
57
58    /**
59     * Constructor
60     *
61     * @access public
62     * @param object Course or Group object
63     * @return
64     */
65    public function __construct($a_container)
66    {
67        global $DIC;
68
69        $lng = $DIC['lng'];
70        $ilCtrl = $DIC['ilCtrl'];
71        $tpl = $DIC['tpl'];
72
73        $this->lng = $lng;
74        $this->lng->loadLanguageModule('crs');
75        $this->lng->loadLanguageModule('grp');
76        $this->lng->loadLanguageModule('ps');
77        $this->lng->loadLanguageModule('membership');
78
79        $this->ctrl = $ilCtrl;
80        $this->tpl = $tpl;
81
82        $this->container = $a_container;
83        $this->ref_id = $this->container->getRefId();
84        $this->obj_id = ilObject::_lookupObjId($this->ref_id);
85        $this->type = ilObject::_lookupType($this->obj_id);
86
87        // Init participants
88        $this->initParticipants();
89
90        // Init waiting list
91        $this->initWaitingList();
92
93        $this->privacy = ilPrivacySettings::_getInstance();
94    }
95
96    /**
97     * Parent object
98     * @return ilObject
99     */
100    public function getContainer()
101    {
102        return $this->container;
103    }
104
105    /**
106     * Get ref
107     * @return type
108     */
109    public function getRefId()
110    {
111        return $this->ref_id;
112    }
113
114    /**
115     * check if registration is possible
116     *
117     * @access protected
118     * @return bool
119     */
120    protected function isRegistrationPossible()
121    {
122        return (bool) $this->registration_possible;
123    }
124
125    /**
126     * set registration disabled
127     *
128     * @access protected
129     * @param bool
130     * @return
131     */
132    protected function enableRegistration($a_status)
133    {
134        $this->registration_possible = $a_status;
135    }
136
137
138    /**
139     * Init participants object (course or group participants)
140     *
141     * @access protected
142     * @return
143     */
144    abstract protected function initParticipants();
145
146    /**
147     * Init waiting list (course or group waiting list)
148     *
149     * @access protected
150     * @abstract
151     * @return
152     */
153    abstract protected function initWaitingList();
154
155    /**
156     * Check if the waiting list is active
157     * Maximum of members exceeded or
158     * any user on the waiting list
159     * @return
160     */
161    abstract protected function isWaitingListActive();
162
163    /**
164     * Get waiting list object
165     * @return object waiting list
166     * @access protected
167     */
168    protected function getWaitingList()
169    {
170        return $this->waiting_list;
171    }
172
173    protected function leaveWaitingList()
174    {
175        global $DIC;
176
177        $ilUser = $DIC['ilUser'];
178        $tree = $DIC['tree'];
179        $ilCtrl = $DIC['ilCtrl'];
180
181        $this->getWaitingList()->removeFromList($ilUser->getId());
182        $parent = $tree->getParentId($this->container->getRefId());
183
184        $message = sprintf(
185            $this->lng->txt($this->container->getType() . '_removed_from_waiting_list'),
186            $this->container->getTitle()
187        );
188        ilUtil::sendSuccess($message, true);
189
190        $ilCtrl->setParameterByClass("ilrepositorygui", "ref_id", $parent);
191        $ilCtrl->redirectByClass("ilrepositorygui", "");
192    }
193
194    /**
195     * Get title for property form
196     *
197     * @access protected
198     * @return string title
199     */
200    abstract protected function getFormTitle();
201
202    /**
203     * fill informations
204     *
205     * @access protected
206     * @return
207     */
208    abstract protected function fillInformations();
209
210    /**
211     * show informations about the registration period
212     *
213     * @access protected
214     */
215    abstract protected function fillRegistrationPeriod();
216
217    /**
218     * show informations about the maximum number of user.
219     *
220     * @access protected
221     * @param
222     * @return
223     */
224    abstract protected function fillMaxMembers();
225
226
227    /**
228     * show informations about registration procedure
229     *
230     * @access protected
231     * @return
232     */
233    abstract protected function fillRegistrationType();
234
235    /**
236     * Show membership limitations
237     *
238     * @access protected
239     * @return
240     */
241    protected function fillMembershipLimitation()
242    {
243        global $DIC;
244
245        $ilAccess = $DIC['ilAccess'];
246        $ilCtrl = $DIC['ilCtrl'];
247
248        include_once('Modules/Course/classes/class.ilObjCourseGrouping.php');
249        if (!$items = ilObjCourseGrouping::_getGroupingItems($this->container)) {
250            return true;
251        }
252
253        $mem = new ilCustomInputGUI($this->lng->txt('groupings'));
254
255        $tpl = new ilTemplate('tpl.membership_limitation_form.html', true, true, 'Services/Membership');
256        $tpl->setVariable('LIMIT_INTRO', $this->lng->txt($this->type . '_grp_info_reg'));
257
258        foreach ($items as $ref_id) {
259            $obj_id = ilObject::_lookupObjId($ref_id);
260            $type = ilObject::_lookupType($obj_id);
261            $title = ilObject::_lookupTitle($obj_id);
262
263            if ($ilAccess->checkAccess('visible', '', $ref_id, $type)) {
264                include_once('./Services/Link/classes/class.ilLink.php');
265                $ilCtrl->setParameterByClass("ilrepositorygui", "ref_id", $ref_id);
266                $tpl->setVariable(
267                    'LINK_ITEM',
268                    $ilCtrl->getLinkTargetByClass("ilrepositorygui", "")
269                );
270                $ilCtrl->setParameterByClass("ilrepositorygui", "ref_id", $_GET["ref_id"]);
271                $tpl->setVariable('ITEM_LINKED_TITLE', $title);
272            } else {
273                $tpl->setVariable('ITEM_TITLE');
274            }
275            $tpl->setCurrentBlock('items');
276            $tpl->setVariable('TYPE_ICON', ilObject::_getIcon($obj_id, 'tiny', $type));
277            $tpl->setVariable('ALT_ICON', $this->lng->txt('obj_' . $type));
278            $tpl->parseCurrentBlock();
279        }
280
281        $mem->setHtml($tpl->get());
282
283
284        if (!ilObjCourseGrouping::_checkGroupingDependencies($this->container)) {
285            $mem->setAlert($this->container->getMessage());
286            $this->enableRegistration(false);
287        }
288        $this->form->addItem($mem);
289    }
290
291    /**
292     * Show user agreement
293     *
294     * @access protected
295     * @return
296     */
297    protected function fillAgreement()
298    {
299        global $DIC;
300
301        $ilUser = $DIC['ilUser'];
302
303        if (!$this->isRegistrationPossible()) {
304            return true;
305        }
306
307        include_once('Modules/Course/classes/Export/class.ilCourseDefinedFieldDefinition.php');
308        if (!$this->privacy->confirmationRequired($this->type) and !ilCourseDefinedFieldDefinition::_hasFields($this->container->getId())) {
309            return true;
310        }
311
312        $this->lng->loadLanguageModule('ps');
313
314        include_once('Services/PrivacySecurity/classes/class.ilExportFieldsInfo.php');
315        $fields_info = ilExportFieldsInfo::_getInstanceByType(ilObject::_lookupType($this->container->getId()));
316
317        if (!count($fields_info->getExportableFields())) {
318            return true;
319        }
320
321        $section = new ilFormSectionHeaderGUI();
322        $section->setTitle($this->lng->txt($this->type . '_usr_agreement'));
323        $this->form->addItem($section);
324
325        include_once './Services/Membership/classes/class.ilMemberAgreementGUI.php';
326        ilMemberAgreementGUI::addExportFieldInfo($this->form, $this->obj_id, $this->type);
327
328
329        ilMemberAgreementGUI::addCustomFields($this->form, $this->obj_id, $this->type);
330
331        // Checkbox agreement
332        if ($this->privacy->confirmationRequired($this->type)) {
333            ilMemberAgreementGUI::addAgreement($this->form, $this->obj_id, $this->type);
334        }
335        return true;
336    }
337
338    /**
339     * Show course defined fields
340     *
341     * @access protected
342     */
343    protected function showCustomFields()
344    {
345        global $DIC;
346
347        $ilUser = $DIC['ilUser'];
348
349        include_once('Modules/Course/classes/Export/class.ilCourseDefinedFieldDefinition.php');
350        include_once('Modules/Course/classes/Export/class.ilCourseUserData.php');
351
352        if (!count($cdf_fields = ilCourseDefinedFieldDefinition::_getFields($this->container->getId()))) {
353            return true;
354        }
355
356        $cdf = new ilNonEditableValueGUI($this->lng->txt('ps_crs_user_fields'));
357        $cdf->setValue($this->lng->txt($this->type . '_ps_cdf_info'));
358        $cdf->setRequired(true);
359
360        foreach ($cdf_fields as $field_obj) {
361            $course_user_data = new ilCourseUserData($ilUser->getId(), $field_obj->getId());
362
363            switch ($field_obj->getType()) {
364                case IL_CDF_TYPE_SELECT:
365                    $select = new ilSelectInputGUI($field_obj->getName(), 'cdf[' . $field_obj->getId() . ']');
366                    $select->setValue(ilUtil::stripSlashes($_POST['cdf'][$field_obj->getId()]));
367                    $select->setOptions($field_obj->prepareSelectBox());
368                    if ($field_obj->isRequired()) {
369                        $select->setRequired(true);
370                    }
371
372                    $cdf->addSubItem($select);
373
374
375                    break;
376
377                case IL_CDF_TYPE_TEXT:
378                    $text = new ilTextInputGUI($field_obj->getName(), 'cdf[' . $field_obj->getId() . ']');
379                    $text->setValue(ilUtil::stripSlashes($_POST['cdf'][$field_obj->getId()]));
380                    $text->setSize(32);
381                    $text->setMaxLength(255);
382                    if ($field_obj->isRequired()) {
383                        $text->setRequired(true);
384                    }
385                    $cdf->addSubItem($text);
386                    break;
387            }
388        }
389        $this->form->addItem($cdf);
390        return true;
391    }
392
393    /**
394     * Check Agreement
395     *
396     * @access protected
397     *
398     */
399    protected function validateAgreement()
400    {
401        global $DIC;
402
403        $ilUser = $DIC['ilUser'];
404
405        if ($_POST['agreement']) {
406            return true;
407        }
408        include_once('Modules/Course/classes/Export/class.ilCourseDefinedFieldDefinition.php');
409        if (!$this->privacy->confirmationRequired($this->type)) {
410            return true;
411        }
412        return false;
413    }
414
415    /**
416     * Check required course fields
417     *
418     * @access protected
419     *
420     */
421    protected function validateCustomFields()
422    {
423        global $DIC;
424
425        $ilUser = $DIC['ilUser'];
426
427
428        $required_fullfilled = true;
429        foreach (ilCourseDefinedFieldDefinition::_getFields($this->container->getId()) as $field_obj) {
430            switch ($field_obj->getType()) {
431                case IL_CDF_TYPE_SELECT:
432
433                    // Split value id from post
434                    list($field_id, $option_id) = explode('_', $_POST['cdf_' . $field_obj->getId()]);
435
436                    $open_answer_indexes = (array) $field_obj->getValueOptions();
437                    if (in_array($option_id, $open_answer_indexes)) {
438                        $value = $_POST['cdf_oa_' . $field_obj->getId() . '_' . $option_id];
439                    } else {
440                        $value = $field_obj->getValueById($option_id);
441                    }
442                    break;
443
444                case IL_CDF_TYPE_TEXT:
445                    $value = $_POST['cdf_' . $field_obj->getId()];
446                    break;
447            }
448
449            $course_user_data = new ilCourseUserData($ilUser->getId(), $field_obj->getId());
450            $course_user_data->setValue($value);
451            $course_user_data->update();
452
453            // #14220
454            if ($field_obj->isRequired() and $value == "") {
455                $required_fullfilled = false;
456            }
457        }
458
459        return $required_fullfilled;
460    }
461
462    /**
463     * Set Agreement accepted
464     *
465     * @access private
466     * @param bool
467     */
468    protected function setAccepted($a_status)
469    {
470        global $DIC;
471
472        $ilUser = $DIC['ilUser'];
473
474        include_once('Modules/Course/classes/Export/class.ilCourseDefinedFieldDefinition.php');
475        if (!$this->privacy->confirmationRequired($this->type) and !ilCourseDefinedFieldDefinition::_hasFields($this->container->getId())) {
476            return true;
477        }
478
479        include_once('Services/Membership/classes/class.ilMemberAgreement.php');
480        $this->agreement = new ilMemberAgreement($ilUser->getId(), $this->container->getId());
481        $this->agreement->setAccepted($a_status);
482        $this->agreement->setAcceptanceTime(time());
483        $this->agreement->save();
484    }
485
486    /**
487     * cancel subscription
488     *
489     * @access public
490     */
491    public function cancel()
492    {
493        global $DIC;
494
495        $tree = $DIC['tree'];
496        $ilCtrl = $DIC['ilCtrl'];
497
498        $ilCtrl->setParameterByClass(
499            "ilrepositorygui",
500            "ref_id",
501            $tree->getParentId($this->container->getRefId())
502        );
503        $ilCtrl->redirectByClass("ilrepositorygui", "");
504    }
505
506    /**
507     * show registration form
508     *
509     * @access public
510     * @param
511     * @return
512     */
513    public function show(ilPropertyFormGUI $form = null)
514    {
515        if (!$form instanceof ilPropertyFormGUI) {
516            $this->initForm();
517        }
518
519        if ($_SESSION["pending_goto"]) {
520            ilUtil::sendInfo($this->lng->txt("reg_goto_parent_membership_info"));
521        }
522
523        $this->tpl->setContent($this->form->getHTML());
524    }
525
526    /**
527     * join
528     *
529     * @access public
530     * @param
531     * @return
532     */
533    public function join()
534    {
535        $form = $this->initForm();
536
537        if (!$form->checkInput() || !$this->validate()) {
538            $form->setValuesByPost();
539            if ($this->join_error) {
540                ilUtil::sendFailure($this->join_error);
541            } else {
542                ilUtil::sendFailure($this->lng->txt('err_check_input'));
543            }
544            $this->show($form);
545            return false;
546        }
547
548        $this->add();
549    }
550
551
552    /**
553     * validate join request
554     *
555     * @access protected
556     * @return bool
557     */
558    protected function validate()
559    {
560        return true;
561    }
562
563    /**
564     * init registration form
565     *
566     * @access protected
567     * @return
568     */
569    protected function initForm()
570    {
571        global $DIC;
572
573        $ilUser = $DIC['ilUser'];
574
575        if (is_object($this->form)) {
576            return true;
577        }
578
579        include_once('./Services/Form/classes/class.ilPropertyFormGUI.php');
580        $this->form = new ilPropertyFormGUI();
581        $this->form->setFormAction($this->ctrl->getFormAction($this, 'join'));
582        $this->form->setTitle($this->getFormTitle());
583
584        $this->fillInformations();
585        $this->fillMembershipLimitation();
586        if ($this->isRegistrationPossible()) {
587            $this->fillRegistrationPeriod();
588        }
589        if ($this->isRegistrationPossible() || $this->participants->isSubscriber($ilUser->getId())) {
590            $this->fillRegistrationType();
591        }
592        if ($this->isRegistrationPossible()) {
593            $this->fillMaxMembers();
594        }
595        if ($this->isRegistrationPossible()) {
596            $this->fillAgreement();
597        }
598        $this->addCommandButtons();
599        return $this->form;
600    }
601
602    /**
603     * Add command buttons
604     * @return
605     */
606    protected function addCommandButtons()
607    {
608        global $DIC;
609
610        $ilUser = $DIC['ilUser'];
611
612        if ($this->isRegistrationPossible() and $this->isWaitingListActive() and !$this->getWaitingList()->isOnList($ilUser->getId())) {
613            $this->form->addCommandButton('join', $this->lng->txt('mem_add_to_wl'));
614            $this->form->addCommandButton('cancel', $this->lng->txt('cancel'));
615        } elseif ($this->isRegistrationPossible() and !$this->getWaitingList()->isOnList($ilUser->getId())) {
616            $this->form->addCommandButton('join', $this->lng->txt('join'));
617            $this->form->addCommandButton('cancel', $this->lng->txt('cancel'));
618        }
619        if ($this->getWaitingList()->isOnList($ilUser->getId())) {
620            ilUtil::sendQuestion(
621                sprintf(
622                    $this->lng->txt($this->container->getType() . '_cancel_waiting_list'),
623                    $this->container->getTitle()
624                )
625            );
626            $this->form->addCommandButton('leaveWaitingList', $this->lng->txt('leave_waiting_list'));
627            $this->form->addCommandButton('cancel', $this->lng->txt('cancel'));
628        }
629    }
630
631    /**
632     * Update subscription message
633     * @return void
634     */
635    protected function updateSubscriptionRequest()
636    {
637        global $DIC;
638
639        $ilUser = $DIC['ilUser'];
640        $tree = $DIC['tree'];
641        $ilCtrl = $DIC['ilCtrl'];
642
643        $this->participants->updateSubject($ilUser->getId(), ilUtil::stripSlashes($_POST['subject']));
644        ilUtil::sendSuccess($this->lng->txt('sub_request_saved'), true);
645        $ilCtrl->setParameterByClass(
646            "ilrepositorygui",
647            "ref_id",
648            $tree->getParentId($this->container->getRefId())
649        );
650        $ilCtrl->redirectByClass("ilrepositorygui", "");
651    }
652
653    protected function cancelSubscriptionRequest()
654    {
655        global $DIC;
656
657        $ilUser = $DIC['ilUser'];
658        $tree = $DIC['tree'];
659        $ilCtrl = $DIC['ilCtrl'];
660
661        $this->participants->deleteSubscriber($ilUser->getId());
662        ilUtil::sendSuccess($this->lng->txt('sub_request_deleted'), true);
663
664        $ilCtrl->setParameterByClass(
665            "ilrepositorygui",
666            "ref_id",
667            $tree->getParentId($this->container->getRefId())
668        );
669        $ilCtrl->redirectByClass("ilrepositorygui", "");
670    }
671}
672