From 5bc97c98627a8373377348cf6bf03c7fcf2f9a33 Mon Sep 17 00:00:00 2001 From: jamiesensei Date: Sat, 14 Oct 2006 12:32:31 +0000 Subject: [PATCH] Fixed a bug with client side validation of form fields. Added some default error messages for rules specified in lang pack as err_{rulename} Use the default by setting the rule message to null. --- course/edit_form.php | 9 +- lang/en_utf8/form.php | 17 +++- lib/formslib.php | 196 ++++++++++++++++++++++++++++++++++++++++-- 3 files changed, 210 insertions(+), 12 deletions(-) diff --git a/course/edit_form.php b/course/edit_form.php index e3bf67d30c..da3884348a 100644 --- a/course/edit_form.php +++ b/course/edit_form.php @@ -299,11 +299,16 @@ class course_edit_form extends moodleform { $costgroup[]= &MoodleQuickForm::createElement('text','cost', '', 'maxlength="6" size="6"'); $costgroup[]= &MoodleQuickForm::createElement('select', 'currency', '', $currencies); $mform->addGroup($costgroup, 'costgrp', get_string('cost'), ' ', false); + //defining a rule for a form element within a group : + $costgrprules=array(); + //set the message to null to tell Moodle to use a default message + //available for most rules, fetched from language pack (err_{rulename}). + $costgrprules['cost'][]=array(null, 'numeric', null, 'client'); + $mform->addGroupRule('costgrp',$costgrprules); $mform->setHelpButton('costgrp', array('cost', get_string('cost')), true); $mform->setDefault('cost', ''); $mform->setDefault('currency', empty($CFG->enrol_currency) ? 'USD' : $CFG->enrol_currency); - // TODO: fix rule usage and add proper error message - //$mform->addRule('cost', get_string('error'), 'numeric', null, 'client'); + } //-------------------------------------------------------------------------------- diff --git a/lang/en_utf8/form.php b/lang/en_utf8/form.php index 7b1754790b..5688ace98c 100644 --- a/lang/en_utf8/form.php +++ b/lang/en_utf8/form.php @@ -1,6 +1,19 @@ name (class $a->classname)'; +//error messages for standard rules +$string['err_required']='You must supply a value here.'; +$string['err_maxlength']='You must enter not more than $a->format characters here.'; +$string['err_minlength']='You must enter at least $a->format characters here.'; +$string['err_numeric']='You must enter a number here.'; +$string['err_rangelength']='You must enter between {$a->format[0]} and {$a->format[1]} characters here.'; +$string['err_email']='You must enter a valid email address here.'; +$string['err_lettersonly']='You must enter only letters here.'; +$string['err_alphanumeric']='You must enter only letters or numbers here.'; +$string['err_nopunctuation']='You must enter no punctuation characters here.'; +$string['err_nonzero']='You must enter a number not starting with a 0 here.'; +$string['err_numeric']='You must enter a number here.'; + ?> \ No newline at end of file diff --git a/lib/formslib.php b/lib/formslib.php index bd20f64a61..489269dcae 100644 --- a/lib/formslib.php +++ b/lib/formslib.php @@ -20,20 +20,22 @@ if ($CFG->debug >= DEBUG_ALL){ } class moodleform { + var $_formname; // form name var $_form; // quickform object definition var $_customdata; // globals workaround function moodleform($action, $customdata=null, $method='post', $target='', $attributes=null) { - $form_name = rtrim(get_class($this), '_form'); + $this->_formname = rtrim(get_class($this), '_form'); $this->_customdata = $customdata; - $this->_form =& new MoodleQuickForm($form_name, $method, $action, $target, $attributes); + $this->_form =& new MoodleQuickForm($this->_formname, $method, $action, $target, $attributes); $this->definition(); $this->_form->addElement('hidden', 'sesskey', null); // automatic sesskey protection $this->_form->setDefault('sesskey', sesskey()); - $this->_form->addElement('hidden', '_qf__', null); // form submission marker - $this->_form->setDefault('_qf__', 1); + $this->_form->addElement('hidden', '_qf__'.$this->_formname, null); // form submission marker + $this->_form->setDefault('_qf__'.$this->_formname, 1); + $this->_form->_setDefaultRuleMessages(); // we have to know all input types before processing submission ;-) $this->_process_submission($method); @@ -51,8 +53,8 @@ class moodleform { } // following trick is needed to enable proper sesskey checks when using GET forms - // the _qf__ serves as a marker that form was actually submitted - if (array_key_exists('_qf__', $submission) and $submission['_qf__'] == 1) { + // the _qf__.$this->_formname serves as a marker that form was actually submitted + if (array_key_exists('_qf__'.$this->_formname, $submission) and $submission['_qf__'.$this->_formname] == 1) { if (!confirm_sesskey()) { error('Incorrect sesskey submitted, form not accepted!'); } @@ -97,6 +99,8 @@ class moodleform { function data_submitted($slashed=true) { if ($this->is_submitted() and $this->is_validated()) { $data = $this->_form->exportValues(null, $slashed); + unset($data['sesskey']); // we do not need to return sesskey + unset($data['_qf__'.$this->_formname]); // we do not need the submission marker too if (empty($data)) { return NULL; } else { @@ -245,8 +249,6 @@ class MoodleQuickForm extends HTML_QuickForm_DHTMLRulesTableless { function exportValues($elementList= null, $addslashes=true){ $unfiltered=parent::exportValues($elementList); - unset($unfiltered['sesskey']); // we do not need to return sesskey - unset($unfiltered['_qf__']); // we do not need the submission marker too if ($addslashes){ return $this->_recursiveFilter('addslashes',$unfiltered); @@ -254,6 +256,184 @@ class MoodleQuickForm extends HTML_QuickForm_DHTMLRulesTableless { return $unfiltered; } } + /** + * Returns the client side validation script + * + * The code here was copied from HTML_QuickForm_DHTMLRulesTableless who copied it from HTML_QuickForm + * and slightly modified to run rules per-element + * Needed to override this because of an error with client side validation of grouped elements. + * + * @access public + * @return string Javascript to perform validation, empty string if no 'client' rules were added + */ + function getValidationScript() + { + if (empty($this->_rules) || empty($this->_attributes['onsubmit'])) { + return ''; + } + + include_once('HTML/QuickForm/RuleRegistry.php'); + $registry =& HTML_QuickForm_RuleRegistry::singleton(); + $test = array(); + $js_escape = array( + "\r" => '\r', + "\n" => '\n', + "\t" => '\t', + "'" => "\\'", + '"' => '\"', + '\\' => '\\\\' + ); + + foreach ($this->_rules as $elementName => $rules) { + foreach ($rules as $rule) { + if ('client' == $rule['validation']) { + unset($element); + + $dependent = isset($rule['dependent']) && is_array($rule['dependent']); + $rule['message'] = strtr($rule['message'], $js_escape); + + if (isset($rule['group'])) { + $group =& $this->getElement($rule['group']); + // No JavaScript validation for frozen elements + if ($group->isFrozen()) { + continue 2; + } + $elements =& $group->getElements(); + foreach (array_keys($elements) as $key) { + if ($elementName == $group->getElementName($key)) { + $element =& $elements[$key]; + break; + } + } + } elseif ($dependent) { + $element = array(); + $element[] =& $this->getElement($elementName); + foreach ($rule['dependent'] as $idx => $elName) { + $element[] =& $this->getElement($elName); + } + } else { + $element =& $this->getElement($elementName); + } + // No JavaScript validation for frozen elements + if (is_object($element) && $element->isFrozen()) { + continue 2; + } elseif (is_array($element)) { + foreach (array_keys($element) as $key) { + if ($element[$key]->isFrozen()) { + continue 3; + } + } + } + // Fix for bug displaying errors for elements in a group + //$test[$elementName][] = $registry->getValidationScript($element, $elementName, $rule); + $test[$elementName][0][] = $registry->getValidationScript($element, $elementName, $rule); + $test[$elementName][1]=$element; + //end of fix + } + } + } + $js = ' +'; + return $js; + } // end func getValidationScript + function _setDefaultRuleMessages(){ + foreach ($this->_rules as $field => $rulesarr){ + foreach ($rulesarr as $key => $rule){ + if ($rule['message']===null){ + $a=new object(); + $a->format=$rule['format']; + $str=get_string('err_'.$rule['type'], 'form', $a); + if (strpos($str, '[[')!==0){ + $this->_rules[$field][$key]['message']=$str; + } + } + } + } + } + } /** -- 2.39.5