| 1 | efrain | 1 | <?php
 | 
        
           |  |  | 2 | // This file is part of Moodle - http://moodle.org/
 | 
        
           |  |  | 3 | //
 | 
        
           |  |  | 4 | // Moodle is free software: you can redistribute it and/or modify
 | 
        
           |  |  | 5 | // it under the terms of the GNU General Public License as published by
 | 
        
           |  |  | 6 | // the Free Software Foundation, either version 3 of the License, or
 | 
        
           |  |  | 7 | // (at your option) any later version.
 | 
        
           |  |  | 8 | //
 | 
        
           |  |  | 9 | // Moodle is distributed in the hope that it will be useful,
 | 
        
           |  |  | 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of
 | 
        
           |  |  | 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | 
        
           |  |  | 12 | // GNU General Public License for more details.
 | 
        
           |  |  | 13 | //
 | 
        
           |  |  | 14 | // You should have received a copy of the GNU General Public License
 | 
        
           |  |  | 15 | // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
 | 
        
           |  |  | 16 |   | 
        
           |  |  | 17 |   | 
        
           |  |  | 18 | /**
 | 
        
           |  |  | 19 |  * select type form element
 | 
        
           |  |  | 20 |  *
 | 
        
           |  |  | 21 |  * Contains HTML class for a select type element
 | 
        
           |  |  | 22 |  *
 | 
        
           |  |  | 23 |  * @package   core_form
 | 
        
           |  |  | 24 |  * @copyright 2006 Jamie Pratt <me@jamiep.org>
 | 
        
           |  |  | 25 |  * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 | 
        
           |  |  | 26 |  */
 | 
        
           |  |  | 27 |   | 
        
           |  |  | 28 | require_once('HTML/QuickForm/select.php');
 | 
        
           |  |  | 29 | require_once('templatable_form_element.php');
 | 
        
           |  |  | 30 |   | 
        
           |  |  | 31 | /**
 | 
        
           |  |  | 32 |  * select type form element
 | 
        
           |  |  | 33 |  *
 | 
        
           |  |  | 34 |  * HTML class for a select type element
 | 
        
           |  |  | 35 |  *
 | 
        
           |  |  | 36 |  * @package   core_form
 | 
        
           |  |  | 37 |  * @category  form
 | 
        
           |  |  | 38 |  * @copyright 2006 Jamie Pratt <me@jamiep.org>
 | 
        
           |  |  | 39 |  * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 | 
        
           |  |  | 40 |  */
 | 
        
           |  |  | 41 | class MoodleQuickForm_select extends HTML_QuickForm_select implements templatable {
 | 
        
           |  |  | 42 |   | 
        
           |  |  | 43 |     use templatable_form_element {
 | 
        
           |  |  | 44 |         export_for_template as export_for_template_base;
 | 
        
           |  |  | 45 |     }
 | 
        
           |  |  | 46 |   | 
        
           |  |  | 47 |     /** @var string html for help button, if empty then no help */
 | 
        
           |  |  | 48 |     var $_helpbutton='';
 | 
        
           |  |  | 49 |   | 
        
           |  |  | 50 |     /** @var bool if true label will be hidden */
 | 
        
           |  |  | 51 |     var $_hiddenLabel=false;
 | 
        
           |  |  | 52 |   | 
        
           |  |  | 53 |     /**
 | 
        
           |  |  | 54 |      * constructor
 | 
        
           |  |  | 55 |      *
 | 
        
           |  |  | 56 |      * @param string $elementName Select name attribute
 | 
        
           |  |  | 57 |      * @param mixed $elementLabel Label(s) for the select
 | 
        
           |  |  | 58 |      * @param mixed $options Data to be used to populate options
 | 
        
           |  |  | 59 |      * @param mixed $attributes Either a typical HTML attribute string or an associative array
 | 
        
           |  |  | 60 |      */
 | 
        
           |  |  | 61 |     public function __construct($elementName=null, $elementLabel=null, $options=null, $attributes=null) {
 | 
        
           |  |  | 62 |         parent::__construct($elementName, $elementLabel, $options, $attributes);
 | 
        
           |  |  | 63 |     }
 | 
        
           |  |  | 64 |   | 
        
           |  |  | 65 |     /**
 | 
        
           |  |  | 66 |      * Old syntax of class constructor. Deprecated in PHP7.
 | 
        
           |  |  | 67 |      *
 | 
        
           |  |  | 68 |      * @deprecated since Moodle 3.1
 | 
        
           |  |  | 69 |      */
 | 
        
           |  |  | 70 |     public function MoodleQuickForm_select($elementName=null, $elementLabel=null, $options=null, $attributes=null) {
 | 
        
           |  |  | 71 |         debugging('Use of class name as constructor is deprecated', DEBUG_DEVELOPER);
 | 
        
           |  |  | 72 |         self::__construct($elementName, $elementLabel, $options, $attributes);
 | 
        
           |  |  | 73 |     }
 | 
        
           |  |  | 74 |   | 
        
           |  |  | 75 |     /**
 | 
        
           |  |  | 76 |      * Sets label to be hidden
 | 
        
           |  |  | 77 |      *
 | 
        
           |  |  | 78 |      * @param bool $hiddenLabel sets if label should be hidden
 | 
        
           |  |  | 79 |      */
 | 
        
           |  |  | 80 |     function setHiddenLabel($hiddenLabel){
 | 
        
           |  |  | 81 |         $this->_hiddenLabel = $hiddenLabel;
 | 
        
           |  |  | 82 |     }
 | 
        
           |  |  | 83 |   | 
        
           |  |  | 84 |     /**
 | 
        
           |  |  | 85 |      * Returns HTML for select form element.
 | 
        
           |  |  | 86 |      *
 | 
        
           |  |  | 87 |      * @return string
 | 
        
           |  |  | 88 |      */
 | 
        
           |  |  | 89 |     function toHtml(){
 | 
        
           |  |  | 90 |         $html = '';
 | 
        
           |  |  | 91 |         if ($this->getMultiple()) {
 | 
        
           |  |  | 92 |             // Adding an hidden field forces the browser to send an empty data even though the user did not
 | 
        
           |  |  | 93 |             // select any element. This value will be cleaned up in self::exportValue() as it will not be part
 | 
        
           |  |  | 94 |             // of the select options.
 | 
        
           |  |  | 95 |             $html .= '<input type="hidden" name="'.$this->getName().'" value="_qf__force_multiselect_submission">';
 | 
        
           |  |  | 96 |         }
 | 
        
           |  |  | 97 |         if ($this->_hiddenLabel){
 | 
        
           |  |  | 98 |             $this->_generateId();
 | 
        
           |  |  | 99 |             $html .= '<label class="accesshide" for="'.$this->getAttribute('id').'" >'.$this->getLabel().'</label>';
 | 
        
           |  |  | 100 |         }
 | 
        
           |  |  | 101 |         $html .= parent::toHtml();
 | 
        
           |  |  | 102 |         return $html;
 | 
        
           |  |  | 103 |     }
 | 
        
           |  |  | 104 |   | 
        
           |  |  | 105 |     /**
 | 
        
           |  |  | 106 |      * get html for help button
 | 
        
           |  |  | 107 |      *
 | 
        
           |  |  | 108 |      * @return string html for help button
 | 
        
           |  |  | 109 |      */
 | 
        
           |  |  | 110 |     function getHelpButton(){
 | 
        
           |  |  | 111 |         return $this->_helpbutton;
 | 
        
           |  |  | 112 |     }
 | 
        
           |  |  | 113 |   | 
        
           |  |  | 114 |     /**
 | 
        
           |  |  | 115 |      * Removes an OPTION from the SELECT
 | 
        
           |  |  | 116 |      *
 | 
        
           |  |  | 117 |      * @param string $value Value for the OPTION to remove
 | 
        
           |  |  | 118 |      * @return void
 | 
        
           |  |  | 119 |      */
 | 
        
           |  |  | 120 |     function removeOption($value)
 | 
        
           |  |  | 121 |     {
 | 
        
           |  |  | 122 |         $key=array_search($value, $this->_values);
 | 
        
           |  |  | 123 |         if ($key!==FALSE and $key!==null) {
 | 
        
           |  |  | 124 |             unset($this->_values[$key]);
 | 
        
           |  |  | 125 |         }
 | 
        
           |  |  | 126 |         foreach ($this->_options as $key=>$option){
 | 
        
           |  |  | 127 |             if ($option['attr']['value']==$value){
 | 
        
           |  |  | 128 |                 unset($this->_options[$key]);
 | 
        
           |  |  | 129 |                 // we must reindex the options because the ugly code in quickforms' select.php expects that keys are 0,1,2,3... !?!?
 | 
        
           |  |  | 130 |                 $this->_options = array_merge($this->_options);
 | 
        
           |  |  | 131 |                 return;
 | 
        
           |  |  | 132 |             }
 | 
        
           |  |  | 133 |         }
 | 
        
           |  |  | 134 |     }
 | 
        
           |  |  | 135 |   | 
        
           |  |  | 136 |     /**
 | 
        
           |  |  | 137 |      * Removes all OPTIONs from the SELECT
 | 
        
           |  |  | 138 |      */
 | 
        
           |  |  | 139 |     function removeOptions()
 | 
        
           |  |  | 140 |     {
 | 
        
           |  |  | 141 |         $this->_options = array();
 | 
        
           |  |  | 142 |     }
 | 
        
           |  |  | 143 |   | 
        
           |  |  | 144 |     /**
 | 
        
           |  |  | 145 |      * Slightly different container template when frozen. Don't want to use a label tag
 | 
        
           |  |  | 146 |      * with a for attribute in that case for the element label but instead use a div.
 | 
        
           |  |  | 147 |      * Templates are defined in renderer constructor.
 | 
        
           |  |  | 148 |      *
 | 
        
           |  |  | 149 |      * @return string
 | 
        
           |  |  | 150 |      */
 | 
        
           |  |  | 151 |     function getElementTemplateType(){
 | 
        
           |  |  | 152 |         if ($this->_flagFrozen){
 | 
        
           |  |  | 153 |             return 'static';
 | 
        
           |  |  | 154 |         } else {
 | 
        
           |  |  | 155 |             return 'default';
 | 
        
           |  |  | 156 |         }
 | 
        
           |  |  | 157 |     }
 | 
        
           |  |  | 158 |   | 
        
           |  |  | 159 |    /**
 | 
        
           |  |  | 160 |     * We check the options and return only the values that _could_ have been
 | 
        
           |  |  | 161 |     * selected. We also return a scalar value if select is not "multiple"
 | 
        
           |  |  | 162 |     *
 | 
        
           |  |  | 163 |     * @param array $submitValues submitted values
 | 
        
           |  |  | 164 |     * @param bool $assoc if true the retured value is associated array
 | 
        
           |  |  | 165 |     * @return mixed
 | 
        
           |  |  | 166 |     */
 | 
        
           |  |  | 167 |     function exportValue(&$submitValues, $assoc = false)
 | 
        
           |  |  | 168 |     {
 | 
        
           |  |  | 169 |         $emptyvalue = $this->getMultiple() ? [] : null;
 | 
        
           |  |  | 170 |         if (empty($this->_options)) {
 | 
        
           |  |  | 171 |             return $this->_prepareValue($emptyvalue, $assoc);
 | 
        
           |  |  | 172 |         }
 | 
        
           |  |  | 173 |   | 
        
           |  |  | 174 |         $value = $this->_findValue($submitValues);
 | 
        
           |  |  | 175 |         if (is_null($value)) {
 | 
        
           |  |  | 176 |             $value = $this->getValue();
 | 
        
           |  |  | 177 |         }
 | 
        
           |  |  | 178 |         $value = (array)$value;
 | 
        
           |  |  | 179 |   | 
        
           |  |  | 180 |         $cleaned = array();
 | 
        
           |  |  | 181 |         foreach ($value as $v) {
 | 
        
           |  |  | 182 |             foreach ($this->_options as $option) {
 | 
        
           |  |  | 183 |                 if ((string)$option['attr']['value'] === (string)$v) {
 | 
        
           |  |  | 184 |                     $cleaned[] = (string)$option['attr']['value'];
 | 
        
           |  |  | 185 |                     break;
 | 
        
           |  |  | 186 |                 }
 | 
        
           |  |  | 187 |             }
 | 
        
           |  |  | 188 |         }
 | 
        
           |  |  | 189 |   | 
        
           |  |  | 190 |         if (empty($cleaned)) {
 | 
        
           |  |  | 191 |             return $this->_prepareValue($emptyvalue, $assoc);
 | 
        
           |  |  | 192 |         }
 | 
        
           |  |  | 193 |         if ($this->getMultiple()) {
 | 
        
           |  |  | 194 |             return $this->_prepareValue($cleaned, $assoc);
 | 
        
           |  |  | 195 |         } else {
 | 
        
           |  |  | 196 |             return $this->_prepareValue($cleaned[0], $assoc);
 | 
        
           |  |  | 197 |         }
 | 
        
           |  |  | 198 |     }
 | 
        
           |  |  | 199 |   | 
        
           |  |  | 200 |     public function export_for_template(renderer_base $output) {
 | 
        
           |  |  | 201 |         $context = $this->export_for_template_base($output);
 | 
        
           |  |  | 202 |   | 
        
           |  |  | 203 |         $options = [];
 | 
        
           |  |  | 204 |         // Standard option attributes.
 | 
        
           |  |  | 205 |         $standardoptionattributes = ['text', 'value', 'selected', 'disabled'];
 | 
        
           |  |  | 206 |         foreach ($this->_options as $option) {
 | 
        
           |  |  | 207 |             if (is_array($this->_values) && in_array( (string) $option['attr']['value'], $this->_values)) {
 | 
        
           |  |  | 208 |                 $this->_updateAttrArray($option['attr'], ['selected' => 'selected']);
 | 
        
           |  |  | 209 |             }
 | 
        
           |  |  | 210 |             $o = [
 | 
        
           |  |  | 211 |                 'text' => $option['text'],
 | 
        
           |  |  | 212 |                 'value' => $option['attr']['value'],
 | 
        
           |  |  | 213 |                 'selected' => !empty($option['attr']['selected']),
 | 
        
           |  |  | 214 |                 'disabled' => !empty($option['attr']['disabled']),
 | 
        
           |  |  | 215 |             ];
 | 
        
           |  |  | 216 |             // Set other attributes.
 | 
        
           |  |  | 217 |             $otheroptionattributes = [];
 | 
        
           |  |  | 218 |             foreach ($option['attr'] as $attr => $value) {
 | 
        
           |  |  | 219 |                 if (!in_array($attr, $standardoptionattributes) && $attr != 'class' && !is_object($value)) {
 | 
        
           |  |  | 220 |                     $otheroptionattributes[] = $attr . '="' . s($value) . '"';
 | 
        
           |  |  | 221 |                 }
 | 
        
           |  |  | 222 |             }
 | 
        
           |  |  | 223 |             $o['optionattributes'] = implode(' ', $otheroptionattributes);
 | 
        
           |  |  | 224 |             $options[] = $o;
 | 
        
           |  |  | 225 |         }
 | 
        
           |  |  | 226 |         $context['options'] = $options;
 | 
        
           |  |  | 227 |         $context['nameraw'] = $this->getName();
 | 
        
           |  |  | 228 |   | 
        
           |  |  | 229 |         return $context;
 | 
        
           |  |  | 230 |     }
 | 
        
           |  |  | 231 | }
 |