diff --git a/lib/formslib.php b/lib/formslib.php index 5b79091d69acf..483db6ea107be 100644 --- a/lib/formslib.php +++ b/lib/formslib.php @@ -131,6 +131,9 @@ abstract class moodleform { /** @var array globals workaround */ protected $_customdata; + /** @var array submitted form data when using mforms with ajax */ + protected $_ajaxformdata; + /** @var object definition_after_data executed flag */ protected $_definition_finalized = false; @@ -156,8 +159,9 @@ abstract class moodleform { * it if you don't need to as the target attribute is deprecated in xhtml strict. * @param mixed $attributes you can pass a string of html attributes here or an array. * @param bool $editable + * @param array $ajaxformdata Forms submitted via ajax, must pass their data here, instead of relying on _GET and _POST. */ - public function __construct($action=null, $customdata=null, $method='post', $target='', $attributes=null, $editable=true) { + public function __construct($action=null, $customdata=null, $method='post', $target='', $attributes=null, $editable=true, $ajaxformdata=null) { global $CFG, $FULLME; // no standard mform in moodle should allow autocomplete with the exception of user signup if (empty($attributes)) { @@ -170,6 +174,7 @@ public function __construct($action=null, $customdata=null, $method='post', $tar } } + if (empty($action)){ // do not rely on PAGE->url here because dev often do not setup $actualurl properly in admin_externalpage_setup() $action = strip_querystring($FULLME); @@ -183,6 +188,7 @@ public function __construct($action=null, $customdata=null, $method='post', $tar // Assign custom data first, so that get_form_identifier can use it. $this->_customdata = $customdata; $this->_formname = $this->get_form_identifier(); + $this->_ajaxformdata = $ajaxformdata; $this->_form = new MoodleQuickForm($this->_formname, $method, $action, $target, $attributes); if (!$editable){ @@ -272,7 +278,9 @@ function focus($name=NULL) { */ function _process_submission($method) { $submission = array(); - if ($method == 'post') { + if (!empty($this->_ajaxformdata) && defined('AJAX_SCRIPT')) { + $submission = $this->_ajaxformdata; + } else if ($method == 'post') { if (!empty($_POST)) { $submission = $_POST; } diff --git a/mod/assign/externallib.php b/mod/assign/externallib.php index 2f769e144f86b..74a7e94a4b925 100644 --- a/mod/assign/externallib.php +++ b/mod/assign/externallib.php @@ -1506,6 +1506,87 @@ public static function unlock_submissions_returns() { return new external_warnings(); } + /** + * Describes the parameters for submit_grading_form webservice. + * @return external_external_function_parameters + * @since Moodle 3.1 + */ + public static function submit_grading_form_parameters() { + return new external_function_parameters( + array( + 'assignmentid' => new external_value(PARAM_INT, 'The assignment id to operate on'), + 'userid' => new external_value(PARAM_INT, 'The user id the submission belongs to'), + 'jsonformdata' => new external_value(PARAM_RAW, 'The data from the grading form, encoded as a json array') + ) + ); + } + + /** + * Submit the logged in users assignment for grading. + * + * @param int $assignmentid The id of the assignment + * @param int $userid The id of the user the submission belongs to. + * @param string $jsonformdata The data from the form, encoded as a json array. + * @return array of warnings to indicate any errors. + * @since Moodle 2.6 + */ + public static function submit_grading_form($assignmentid, $userid, $jsonformdata) { + global $CFG, $USER; + + require_once($CFG->dirroot . '/mod/assign/locallib.php'); + require_once($CFG->dirroot . '/mod/assign/gradeform.php'); + + $params = self::validate_parameters(self::submit_grading_form_parameters(), + array('assignmentid' => $assignmentid, + 'userid' => $userid, + 'jsonformdata' => $jsonformdata)); + + $cm = get_coursemodule_from_instance('assign', $params['assignmentid'], 0, false, MUST_EXIST); + $context = context_module::instance($cm->id); + self::validate_context($context); + + $assignment = new assign($context, $cm, null); + + $serialiseddata = json_decode($params['jsonformdata']); + + $data = array(); + parse_str($serialiseddata, $data); + + $warnings = array(); + + $options = array('userid'=>$params['userid'], + 'attemptnumber'=>$data['attemptnumber'], + 'rownum'=>0, + 'gradingpanel' => true); + + $customdata = (object) $data; + $formparams = array($assignment, $customdata, $options); + + // Data is injected into the form by the last param for the constructor. + $mform = new mod_assign_grade_form(null, $formparams, 'post', '', null, true, $data); + $validateddata = $mform->get_data(); + + if ($validateddata) { + $assignment->save_grade($params['userid'], $validateddata); + } else { + $warnings[] = self::generate_warning($params['assignmentid'], + 'couldnotsavegrade', + 'Form validation failed.'); + } + + + return $warnings; + } + + /** + * Describes the return for submit_grading_form + * @return external_external_function_parameters + * @since Moodle 3.1 + */ + public static function submit_grading_form_returns() { + return new external_warnings(); + } + /** * Describes the parameters for submit_for_grading * @return external_external_function_parameters