evalform.class.php 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572
  1. <?php
  2. /* For licensing terms, see /license.txt */
  3. /*$htmlHeadXtra[] = '<script type="text/javascript">
  4. function setFocus(){
  5. $("#evaluation_title").focus();
  6. }
  7. $(document).ready(function () {
  8. setFocus();
  9. });
  10. </script>';*/
  11. /**
  12. * Class EvalForm
  13. *
  14. * Extends FormValidator with add&edit forms for evaluations
  15. * @author Stijn Konings
  16. * @package chamilo.gradebook
  17. */
  18. class EvalForm extends FormValidator
  19. {
  20. const TYPE_ADD = 1;
  21. const TYPE_EDIT = 2;
  22. const TYPE_MOVE = 3;
  23. const TYPE_RESULT_ADD = 4;
  24. const TYPE_RESULT_EDIT = 5;
  25. const TYPE_ALL_RESULTS_EDIT = 6;
  26. const TYPE_ADD_USERS_TO_EVAL = 7;
  27. private $evaluation_object;
  28. private $result_object;
  29. private $extra;
  30. /**
  31. * Builds a form containing form items based on a given parameter
  32. * @param int form_type 1=add, 2=edit,3=move,4=result_add
  33. * @param obj cat_obj the category object
  34. * @param obj res_obj the result object
  35. * @param string form name
  36. * @param method
  37. * @param action
  38. */
  39. public function __construct($form_type, $evaluation_object, $result_object, $form_name, $method = 'post', $action = null, $extra1 = null, $extra2 = null)
  40. {
  41. parent::__construct($form_name, $method, $action);
  42. if (isset($evaluation_object)) {
  43. $this->evaluation_object = $evaluation_object;
  44. }
  45. if (isset($result_object)) {
  46. $this->result_object = $result_object;
  47. }
  48. if (isset($extra1)) {
  49. $this->extra = $extra1;
  50. }
  51. switch ($form_type) {
  52. case self :: TYPE_EDIT:
  53. $this->build_editing_form();
  54. break;
  55. case self :: TYPE_ADD:
  56. $this->build_add_form();
  57. break;
  58. case self :: TYPE_MOVE:
  59. $this->build_editing_form();
  60. break;
  61. case self :: TYPE_RESULT_ADD:
  62. $this->build_result_add_form();
  63. break;
  64. case self :: TYPE_RESULT_EDIT:
  65. $this->build_result_edit_form();
  66. break;
  67. case self :: TYPE_ALL_RESULTS_EDIT:
  68. $this->build_all_results_edit_form();
  69. break;
  70. case self :: TYPE_ADD_USERS_TO_EVAL:
  71. $this->build_add_user_to_eval();
  72. break;
  73. }
  74. $this->setDefaults();
  75. }
  76. /**
  77. * This form will build a form to add users to an evaluation
  78. */
  79. protected function build_add_user_to_eval()
  80. {
  81. $this->addElement('header', get_lang('ChooseUser'));
  82. $select = $this->addElement('select', 'firstLetterUser', get_lang('FirstLetter'), null, array(
  83. 'onchange' => 'document.add_users_to_evaluation.submit()'
  84. ));
  85. $select->addOption('', '');
  86. for ($i = 65; $i <= 90; $i ++) {
  87. $letter = chr($i);
  88. if (isset($this->extra) && $this->extra == $letter) {
  89. $select->addOption($letter, $letter, 'selected');
  90. } else {
  91. $select->addOption($letter, $letter);
  92. }
  93. }
  94. $select = $this->addElement('select', 'add_users', null, null, array(
  95. 'multiple' => 'multiple',
  96. 'size' => '15',
  97. 'style' => 'width:250px'
  98. ));
  99. foreach ($this->evaluation_object->get_not_subscribed_students() as $user) {
  100. if ((!isset($this->extra)) || empty($this->extra) || api_strtoupper(api_substr($user[1], 0, 1)) == $this->extra) {
  101. $select->addoption($user[1] . ' ' . $user[2] . ' (' . $user[3] . ')', $user[0]);
  102. }
  103. }
  104. $this->addButtonCreate(get_lang('AddUserToEval'), 'submit_button');
  105. }
  106. /**
  107. * This function builds a form to edit all results in an evaluation
  108. */
  109. protected function build_all_results_edit_form()
  110. {
  111. //extra field for check on maxvalue
  112. $this->addElement('hidden', 'maxvalue', $this->evaluation_object->get_max());
  113. $this->addElement('hidden', 'minvalue', 0);
  114. $this->addElement('header', get_lang('EditResult'));
  115. $renderer = & $this->defaultRenderer();
  116. // set new form template
  117. $form_template = '<form{attributes}>
  118. <table class="data_table" border="0" cellpadding="5" cellspacing="5">{content}
  119. </table>
  120. </form>';
  121. $renderer->setFormTemplate($form_template);
  122. if (api_is_western_name_order()) {
  123. $renderer->setHeaderTemplate(
  124. '<tr>
  125. <th>' . get_lang('OfficialCode') . '</th>
  126. <th>' . get_lang('UserName') . '</th>
  127. <th>' . get_lang('FirstName') . '</th>
  128. <th>' . get_lang('LastName') . '</th>
  129. <th>' . get_lang('Qualify') . '</th>
  130. </tr>'
  131. );
  132. } else {
  133. $renderer->setHeaderTemplate(
  134. '<tr>
  135. <th>' . get_lang('OfficialCode') . '</th>
  136. <th>' . get_lang('UserName') . '</th>
  137. <th>' . get_lang('LastName') . '</th>
  138. <th>' . get_lang('FirstName') . '</th>
  139. <th>' . get_lang('Qualify') . '</th>
  140. </tr>'
  141. );
  142. }
  143. $template_submit = '<tr>
  144. <td colspan="4" ></td>
  145. <td >
  146. {element}
  147. <!-- BEGIN error --><br /><span style="color: #ff0000;font-size:10px">{error}</span><!-- END error -->
  148. </td>
  149. </tr>';
  150. $results_and_users = array();
  151. foreach ($this->result_object as $result) {
  152. $user = api_get_user_info($result->get_user_id());
  153. $results_and_users[] = array('result' => $result, 'user' => $user);
  154. }
  155. usort($results_and_users, array('EvalForm', 'sort_by_user'));
  156. $defaults = array();
  157. foreach ($results_and_users as $result_and_user) {
  158. $user = $result_and_user['user'];
  159. $result = $result_and_user['result'];
  160. $renderer = &$this->defaultRenderer();
  161. $this->addText('score[' . $result->get_id() . ']', $this->build_stud_label($user['user_id'], $user['username'], $user['lastname'], $user['firstname']), false, array('class' => "span2",
  162. 'maxlength' => 5));
  163. $this->addRule('score[' . $result->get_id() . ']', get_lang('OnlyNumbers'), 'numeric');
  164. $this->addRule(array(
  165. 'score[' . $result->get_id() . ']', 'maxvalue'), get_lang('OverMax'), 'compare', '<=');
  166. $this->addRule(array(
  167. 'score[' . $result->get_id() . ']', 'minvalue'), get_lang('UnderMin'), 'compare', '>=');
  168. $defaults['score[' . $result->get_id() . ']'] = $result->get_score();
  169. if (api_is_western_name_order()) {
  170. $user_info = '<td align="left" >' . $user['firstname'] . '</td>';
  171. $user_info .= '<td align="left" >' . $user['lastname'] . '</td>';
  172. } else {
  173. $user_info = '<td align="left" >' . $user['lastname'] . '</td>';
  174. $user_info .= '<td align="left" >' . $user['firstname'] . '</td>';
  175. }
  176. $template = '<tr>
  177. <td align="left" >' . $user['official_code'] . '</td>
  178. <td align="left" >' . $user['username'] . '</td>
  179. ' . $user_info . '
  180. <td align="left">{element} / ' . $this->evaluation_object->get_max() . '
  181. <!-- BEGIN error --><br /><span style="color: #ff0000;font-size:10px">{error}</span><!-- END error -->
  182. </td>
  183. </tr>';
  184. $renderer->setElementTemplate($template, 'score[' . $result->get_id() . ']');
  185. }
  186. $this->setDefaults($defaults);
  187. $this->addButtonSave(get_lang('EditResult'), 'submit');
  188. $renderer->setElementTemplate($template_submit, 'submit');
  189. }
  190. /**
  191. * This function builds a form to move an item to another category
  192. *
  193. */
  194. protected function build_move_form()
  195. {
  196. $renderer = & $this->defaultRenderer();
  197. $renderer->setCustomElementTemplate('<span>{element}</span> ');
  198. $this->addElement('static', null, null, '"' . $this->evaluation_object->get_name() . '" ');
  199. $this->addElement('static', null, null, get_lang('MoveTo') . ' : ');
  200. $select = $this->addElement('select', 'move_cat', null, null);
  201. $line = '';
  202. foreach ($this->evaluation_object->get_target_categories() as $cat) {
  203. for ($i = 0; $i < $cat[2]; $i++) {
  204. $line .= '&mdash;';
  205. }
  206. $select->addoption($line . ' ' . $cat[1], $cat[0]);
  207. $line = '';
  208. }
  209. $this->addButtonSave(get_lang('Ok'), 'submit');
  210. }
  211. /**
  212. * Builds a result form containing inputs for all students with a given course_code
  213. */
  214. protected function build_result_add_form()
  215. {
  216. $renderer = & $this->defaultRenderer();
  217. $renderer->setFormTemplate(
  218. '<form{attributes}>
  219. <table class="data_table">
  220. {content}
  221. </table>
  222. </form>'
  223. );
  224. $tblusers = GradebookUtils::get_users_in_course($this->evaluation_object->get_course_code());
  225. $nr_users = 0;
  226. //extra field for check on maxvalue
  227. $this->addElement('hidden', 'maxvalue', $this->evaluation_object->get_max());
  228. $this->addElement('hidden', 'minvalue', 0);
  229. $this->addElement('header', get_lang('AddResult'));
  230. if (api_is_western_name_order()) {
  231. $renderer->setHeaderTemplate(
  232. '<tr>
  233. <th>' . get_lang('OfficialCode') . '</th>
  234. <th>' . get_lang('UserName') . '</th>
  235. <th>' . get_lang('FirstName') . '</th>
  236. <th>' . get_lang('LastName') . '</th>
  237. <th>' . get_lang('Qualify') . '</th>
  238. </tr>'
  239. );
  240. } else {
  241. $renderer->setHeaderTemplate(
  242. '<tr>
  243. <th>' . get_lang('OfficialCode') . '</th>
  244. <th>' . get_lang('UserName') . '</th>
  245. <th>' . get_lang('LastName') . '</th>
  246. <th>' . get_lang('FirstName') . '</th>
  247. <th>' . get_lang('Qualify') . '</th>
  248. </tr>'
  249. );
  250. }
  251. $firstUser = true;
  252. foreach ($tblusers as $user) {
  253. $element_name = 'score[' . $user[0] . ']';
  254. $scoreColumnProperties = array('class' => 'span1', 'maxlength' => 5);
  255. if ($firstUser) {
  256. $scoreColumnProperties['autofocus'] = '';
  257. $firstUser = false;
  258. }
  259. //user_id, user.username, lastname, firstname
  260. $this->addText($element_name, $this->build_stud_label($user[0], $user[1], $user[2], $user[3]), false, $scoreColumnProperties);
  261. $this->addRule($element_name, get_lang('OnlyNumbers'), 'numeric');
  262. $this->addRule(array($element_name, 'maxvalue'), get_lang('OverMax'), 'compare', '<=');
  263. $this->addRule(array($element_name, 'minvalue'), get_lang('UnderMin'), 'compare', '>=');
  264. if (api_is_western_name_order()) {
  265. $user_info = '<td align="left" >' . $user[3] . '</td>';
  266. $user_info .= '<td align="left" >' . $user[2] . '</td>';
  267. } else {
  268. $user_info = '<td align="left" >' . $user[2] . '</td>';
  269. $user_info .= '<td align="left" >' . $user[3] . '</td>';
  270. }
  271. $nr_users++;
  272. $template = '<tr>
  273. <td align="left" >' . $user[4] . '</td>
  274. <td align="left" >' . $user[1] . '</td>
  275. ' . $user_info . '
  276. <td align="left">{element} / ' . $this->evaluation_object->get_max() . '
  277. <!-- BEGIN error --><br /><span style="color: #ff0000;font-size:10px">{error}</span><!-- END error -->
  278. </td>
  279. </tr>';
  280. $renderer->setElementTemplate($template, $element_name);
  281. }
  282. $this->addElement('hidden', 'nr_users', $nr_users);
  283. $this->addElement('hidden', 'evaluation_id', $this->result_object->get_evaluation_id());
  284. $this->addButtonSave(get_lang('AddResult'), 'submit');
  285. $template_submit = '<tr>
  286. <td colspan="4" ></td>
  287. <td >
  288. {element}
  289. <!-- BEGIN error --><br /><span style="color: #ff0000;font-size:10px">{error}</span><!-- END error -->
  290. </td>
  291. </tr>';
  292. $renderer->setElementTemplate($template_submit, 'submit');
  293. }
  294. /**
  295. * Builds a form to edit a result
  296. */
  297. protected function build_result_edit_form()
  298. {
  299. $this->setDefaults(array(
  300. 'score' => $this->result_object->get_score(),
  301. 'maximum' => $this->evaluation_object->get_max()
  302. ));
  303. $userinfo = api_get_user_info($this->result_object->get_user_id());
  304. $renderer = & $this->defaultRenderer();
  305. $renderer->setCustomElementTemplate('<span>{element}</span> ');
  306. $this->addElement('label', get_lang('User'), $userinfo['complete_name']);
  307. $this->addText('score', array(get_lang('Score'), null, '/ ' . $this->evaluation_object->get_max()), false, array(
  308. 'size' => '4',
  309. 'class' => 'span1',
  310. 'maxlength' => '5'
  311. ));
  312. /* $this->addText('maximum', null, false, array (
  313. 'size' => '4',
  314. 'maxlength' => '5',
  315. 'disabled' => 'disabled'
  316. )); */
  317. $this->addButtonSave(get_lang('Edit'), 'submit');
  318. $this->addElement('hidden', 'minvalue', 0);
  319. $this->addElement('hidden', 'hid_user_id', $this->result_object->get_user_id());
  320. $this->addElement('hidden', 'maxvalue', $this->evaluation_object->get_max());
  321. $this->addRule('score', get_lang('OnlyNumbers'), 'numeric', null, 'client');
  322. $this->addRule(array(
  323. 'score',
  324. 'maxvalue'
  325. ), get_lang('OverMax'), 'compare', '<=', 'client');
  326. $this->addRule(array(
  327. 'score',
  328. 'minvalue'
  329. ), get_lang('UnderMin'), 'compare', '>=', 'client');
  330. }
  331. /**
  332. * Builds a form to add an evaluation
  333. */
  334. protected function build_add_form()
  335. {
  336. $this->setDefaults(array('hid_user_id' => $this->evaluation_object->get_user_id(),
  337. 'hid_category_id' => $this->evaluation_object->get_category_id(),
  338. 'hid_course_code' => $this->evaluation_object->get_course_code(), 'created_at' => api_get_utc_datetime()));
  339. $this->build_basic_form(0);
  340. if ($this->evaluation_object->get_course_code() == null) {
  341. $this->addElement('checkbox', 'adduser', null, get_lang('AddUserToEval'));
  342. } else {
  343. $this->addElement('checkbox', 'addresult', null, get_lang('AddResult'));
  344. }
  345. $this->addButtonCreate(get_lang('AddAssessment'), 'submit');
  346. }
  347. /**
  348. * Builds a form to edit an evaluation
  349. */
  350. protected function build_editing_form()
  351. {
  352. $parent_cat = Category :: load($this->evaluation_object->get_category_id());
  353. //@TODO $weight_mask is replaced?
  354. if ($parent_cat[0]->get_parent_id() == 0) {
  355. $weight_mask = $this->evaluation_object->get_weight();
  356. } else {
  357. $cat = Category :: load($parent_cat[0]->get_parent_id());
  358. $global_weight = $cat[0]->get_weight();
  359. $weight_mask = $global_weight * $this->evaluation_object->get_weight() / $parent_cat[0]->get_weight();
  360. }
  361. $weight = $weight_mask = $this->evaluation_object->get_weight();
  362. $this->setDefaults(array('hid_id' => $this->evaluation_object->get_id(),
  363. 'name' => $this->evaluation_object->get_name(),
  364. 'description' => $this->evaluation_object->get_description(),
  365. 'hid_user_id' => $this->evaluation_object->get_user_id(),
  366. 'hid_course_code' => $this->evaluation_object->get_course_code(),
  367. 'hid_category_id' => $this->evaluation_object->get_category_id(),
  368. 'created_at' => api_get_utc_datetime($this->evaluation_object->get_date()),
  369. 'weight' => $weight,
  370. 'weight_mask' => $weight_mask,
  371. 'max' => $this->evaluation_object->get_max(),
  372. 'visible' => $this->evaluation_object->is_visible()));
  373. $id_current = isset($this->id) ? $this->id : null;
  374. $this->addElement('hidden', 'hid_id', $id_current);
  375. $this->build_basic_form(1);
  376. $this->addButtonSave(get_lang('ModifyEvaluation'), 'submit');
  377. }
  378. /**
  379. * Builds a basic form that is used in add and edit
  380. */
  381. private function build_basic_form($edit = 0)
  382. {
  383. $form_title = get_lang('NewEvaluation');
  384. if (!empty($_GET['editeval']) && $_GET['editeval'] == 1) {
  385. $form_title = get_lang('EditEvaluation');
  386. }
  387. $this->addElement('header', $form_title);
  388. $this->addElement('hidden', 'zero', 0);
  389. $this->addElement('hidden', 'hid_user_id');
  390. $this->addElement('hidden', 'hid_course_code');
  391. $this->addText('name', get_lang('EvaluationName'), true, array(
  392. 'class' => 'span3',
  393. 'maxlength' => '50',
  394. 'id' => 'evaluation_title'
  395. ));
  396. $cat_id = $this->evaluation_object->get_category_id();
  397. $session_id = api_get_session_id();
  398. $course_code = api_get_course_id();
  399. $all_categories = Category :: load(null, null, $course_code, null, null, $session_id, false);
  400. if (count($all_categories) == 1) {
  401. $this->addElement('hidden', 'hid_category_id', $cat_id);
  402. } else {
  403. $select_gradebook = $this->addElement('select', 'hid_category_id', get_lang('SelectGradebook'), array(), array('id' => 'hid_category_id'));
  404. $this->addRule('hid_category_id', get_lang('ThisFieldIsRequired'), 'nonzero');
  405. $default_weight = 0;
  406. if (!empty($all_categories)) {
  407. foreach ($all_categories as $my_cat) {
  408. if ($my_cat->get_course_code() == api_get_course_id()) {
  409. $grade_model_id = $my_cat->get_grade_model_id();
  410. if (empty($grade_model_id)) {
  411. if ($my_cat->get_parent_id() == 0) {
  412. $default_weight = $my_cat->get_weight();
  413. $select_gradebook->addoption(get_lang('Default'), $my_cat->get_id());
  414. $cats_added[] = $my_cat->get_id();
  415. } else {
  416. $select_gradebook->addoption($my_cat->get_name(), $my_cat->get_id());
  417. $cats_added[] = $my_cat->get_id();
  418. }
  419. } else {
  420. $select_gradebook->addoption(get_lang('Select'), 0);
  421. }
  422. if ($this->evaluation_object->get_category_id() == $my_cat->get_id()) {
  423. $default_weight = $my_cat->get_weight();
  424. }
  425. }
  426. }
  427. }
  428. }
  429. $this->addText('weight_mask', array(get_lang('Weight'), null, ' [0 .. <span id="max_weight">' . $all_categories[0]->get_weight() . '</span>] '), true, array(
  430. 'size' => '4',
  431. 'maxlength' => '5',
  432. 'class' => 'span1'
  433. ));
  434. /* $this->addText('weight', array(null, null, '/ <span id="max_weight">'.$default_weight.'</span>'), true, array (
  435. 'size' => '4',
  436. 'maxlength' => '5',
  437. 'class' => 'span1'
  438. )); */
  439. if ($edit) {
  440. if (!$this->evaluation_object->has_results()) {
  441. $this->addText('max', get_lang('QualificationNumeric'), true, array(
  442. 'class' => 'span1',
  443. 'maxlength' => '5'
  444. ));
  445. } else {
  446. $this->addText('max', array(get_lang('QualificationNumeric'), get_lang('CannotChangeTheMaxNote')), false, array(
  447. 'class' => 'span1',
  448. 'maxlength' => '5',
  449. 'disabled' => 'disabled'
  450. ));
  451. }
  452. } else {
  453. $this->addText('max', get_lang('QualificationNumeric'), true, array(
  454. 'class' => 'span1',
  455. 'maxlength' => '5'
  456. ));
  457. $default_max = api_get_setting('gradebook_default_weight');
  458. $defaults['max'] = isset($default_max) ? $default_max : 100;
  459. $this->setDefaults($defaults);
  460. }
  461. $this->addElement('textarea', 'description', get_lang('Description'));
  462. $this->addRule('hid_category_id', get_lang('ThisFieldIsRequired'), 'required');
  463. $this->addElement('checkbox', 'visible', null, get_lang('Visible'));
  464. $this->addRule('weight_mask', get_lang('OnlyNumbers'), 'numeric');
  465. $this->addRule(array('weight_mask', 'zero'), get_lang('NegativeValue'), 'compare', '>=');
  466. $this->addRule('max', get_lang('OnlyNumbers'), 'numeric');
  467. $this->addRule(array('max', 'zero'), get_lang('NegativeValue'), 'compare', '>=');
  468. $setting = api_get_setting('tool_visible_by_default_at_creation');
  469. $visibility_default = 1;
  470. if (isset($setting['gradebook']) && $setting['gradebook'] == 'false') {
  471. $visibility_default = 0;
  472. }
  473. $this->setDefaults(array('visible' => $visibility_default));
  474. }
  475. function display()
  476. {
  477. parent :: display();
  478. }
  479. function setDefaults($defaults = array(), $filter = null)
  480. {
  481. parent :: setDefaults($defaults, $filter);
  482. }
  483. private function build_stud_label($id, $username, $lastname, $firstname)
  484. {
  485. $opendocurl_start = '';
  486. $opendocurl_end = '';
  487. // evaluation's origin is a link
  488. if ($this->evaluation_object->get_category_id() < 0) {
  489. $link = LinkFactory :: get_evaluation_link($this->evaluation_object->get_id());
  490. $doc_url = $link->get_view_url($id);
  491. if ($doc_url != null) {
  492. $opendocurl_start .= '<a href="' . $doc_url . '" target="_blank">';
  493. $opendocurl_end = '</a>';
  494. }
  495. }
  496. return $opendocurl_start . api_get_person_name($firstname, $lastname) . ' (' . $username . ')' . $opendocurl_end;
  497. }
  498. function sort_by_user($item1, $item2)
  499. {
  500. $user1 = $item1['user'];
  501. $user2 = $item2['user'];
  502. if (api_sort_by_first_name()) {
  503. $result = api_strcmp($user1['firstname'], $user2['firstname']);
  504. if ($result == 0) {
  505. return api_strcmp($user1['lastname'], $user2['lastname']);
  506. }
  507. } else {
  508. $result = api_strcmp($user1['lastname'], $user2['lastname']);
  509. if ($result == 0) {
  510. return api_strcmp($user1['firstname'], $user2['firstname']);
  511. }
  512. }
  513. return $result;
  514. }
  515. }