MDL-30637 Simplify moodle forms

Make the forms easier to use and navigate by adding functionality to
collapse and extend form sections (headers). The logic is as follows:

If form contains 2 and less sections (headers):

* Display the form as non-collapsible at all.
* The point above can be overridden if developer marks the section as expanded
  in form definition (e.g. $mform->setExpanded('foo'));

If form contains 3 and more sections (headers):

* always expanding the first section and closing all others by default;
* always expanding a section containing at least one "required" element;
* expanding any section which contains validation errors after submission;
* expanding any section which was previously open on previous submit (e.g. when
  adding new choices);
* expanding the section which is marked as expanded in form definition (e.g.
  $mform->setExpanded('foo');
This commit is contained in:
Ruslan Kabalin 2013-02-07 14:13:36 +00:00
parent 1918a2452e
commit a4067bfc48
3 changed files with 259 additions and 19 deletions

96
lib/form/yui/shortforms/shortforms.js vendored Normal file
View file

@ -0,0 +1,96 @@
YUI.add('moodle-form-shortforms', function(Y) {
/**
* Provides the form shortforms class
*
* @module moodle-form-shortforms
*/
/**
* A class for a shortforms
*
* @param {Object} config Object literal specifying shortforms configuration properties.
* @class M.form.shortforms
* @constructor
* @extends Y.Base
*/
function SHORTFORMS(config) {
SHORTFORMS.superclass.constructor.apply(this, [config]);
}
var SELECTORS = {
FIELDSETCOLLAPSIBLE : 'fieldset.collapsible',
LEGENDFTOGGLER : 'legend.ftoggler'
},
CSS = {
COLLAPSED : 'collapsed',
FHEADER : 'fheader',
JSPROCESSED : 'jsprocessed'
},
ATTRS = {};
/**
* Static property provides a string to identify the JavaScript class.
*
* @property NAME
* @type String
* @static
*/
SHORTFORMS.NAME = 'moodle-form-shortforms';
/**
* Static property used to define the default attribute configuration for the Shortform.
*
* @property ATTRS
* @type String
* @static
*/
SHORTFORMS.ATTRS = ATTRS;
/**
* The form ID attribute definition
*
* @attribute formid
* @type String
* @default ''
* @writeOnce
*/
ATTRS.formid = {
value : null
};
Y.extend(SHORTFORMS, Y.Base, {
initializer : function() {
var fieldlist = Y.Node.all('#'+this.get('formid')+' '+SELECTORS.FIELDSETCOLLAPSIBLE);
// Look through collapsible fieldset divs
fieldlist.each(this.process_fieldset, this);
// Subscribe collapsible fieldsets to click event
Y.one('#'+this.get('formid')).delegate('click', this.switch_state, SELECTORS.FIELDSETCOLLAPSIBLE+' .'+CSS.FHEADER);
},
process_fieldset : function(fieldset) {
fieldset.addClass(CSS.JSPROCESSED);
// Get legend element
var legendelement = fieldset.one(SELECTORS.LEGENDFTOGGLER);
// Turn headers to links for accessibility
var headerlink = Y.Node.create('<a href="#"></a>');
headerlink.addClass(CSS.FHEADER);
headerlink.appendChild(legendelement.get('firstChild'));
legendelement.prepend(headerlink);
},
switch_state : function(e) {
e.preventDefault();
var fieldset = this.ancestor(SELECTORS.FIELDSETCOLLAPSIBLE);
// toggle collapsed class
fieldset.toggleClass(CSS.COLLAPSED);
// get corresponding hidden variable
var statuselement = new Y.one('input[name=mform_isexpanded_'+fieldset.get('id')+']');
// and invert it
statuselement.set('value', Math.abs(Number(statuselement.get('value'))-1));
}
});
M.form = M.form || {};
M.form.shortforms = M.form.shortforms || function(params) {
return new SHORTFORMS(params);
};
}, '@VERSION@', {requires:['base', 'node', 'selector-css3']});