Permalink
Browse files

MDL-38455 form: More consistency in section states

- A short form of 2 sections has collapsible sections;
- The second section is expanded by default if the form has 2 sections;
- The collapsed state by setExpanded can override the state in which
  the section was when it was submitted by the user;
- A header containing a required field or one that has an error
  will never be collapsed.
  • Loading branch information...
1 parent 8963212 commit 90a7e556af0a13df70e923ec8df584718d47f148 @FMCorz FMCorz committed Mar 13, 2013
Showing with 45 additions and 40 deletions.
  1. +45 −40 lib/formslib.php
View
@@ -1310,7 +1310,9 @@ class MoodleQuickForm extends HTML_QuickForm_DHTMLRulesTableless {
var $_advancedElements = array();
/**
- * Array whose keys are element names and the the boolean values reflect the current state. If the key exists this is a collapsible element.
+ * Array whose keys are element names and values are the desired collapsible state.
+ * True for collapsed, False for expanded. If not present, set to default in
+ * {@link self::accept()}.
*
* @var array
*/
@@ -1340,14 +1342,6 @@ class MoodleQuickForm extends HTML_QuickForm_DHTMLRulesTableless {
*/
var $_pageparams = '';
- /**
- * The maximum number of headers the form should contain in order not to be
- * defined as collapsible.
- *
- * @var int
- */
- var $_non_collapsible_headers = 2;
-
/**
* Class constructor - same parameters as HTML_QuickForm_DHTMLRulesTableless
*
@@ -1402,7 +1396,7 @@ function MoodleQuickForm($formName, $method, $action, $target='', $attributes=nu
* @param string $elementName group or element name (not the element name of something inside a group).
* @param bool $advanced default true sets the element to advanced. False removes advanced mark.
*/
- function setAdvanced($elementName, $advanced=true){
+ function setAdvanced($elementName, $advanced = true) {
if ($advanced){
$this->_advancedElements[$elementName]='';
} elseif (isset($this->_advancedElements[$elementName])) {
@@ -1416,9 +1410,11 @@ function setAdvanced($elementName, $advanced=true){
*
* @param string $headername header element name
* @param boolean $expanded default true sets the element to expanded. False makes the element collapsed.
+ * @param boolean $ignoreuserstate override the state regardless of the state it was on when
+ * the form was submitted.
* @return void
*/
- function setExpanded($headername, $expanded=true){
+ function setExpanded($headername, $expanded = true, $ignoreuserstate = false) {
if (empty($headername)) {
return;
}
@@ -1432,9 +1428,9 @@ function setExpanded($headername, $expanded=true){
$headerid = $element->getAttribute('id');
}
if ($this->getElementType('mform_isexpanded_' . $headerid) === false) {
- // See if we the form has been submitted already.
+ // See if the form has been submitted already.
$formexpanded = optional_param('mform_isexpanded_' . $headerid, -1, PARAM_INT);
- if (!$expanded && $formexpanded != -1) {
+ if (!$ignoreuserstate && $formexpanded != -1) {
// Override expanded state with the form variable.
$expanded = $formexpanded;
}
@@ -1578,44 +1574,53 @@ function accept(&$renderer) {
}
$renderer->setAdvancedElements($this->_advancedElements);
}
- if (method_exists($renderer, 'setCollapsibleElements') && !$this->_disableShortforms){
- // Check how many headers we have in total, if less than $_non_collapsible_headers,
- // the form should not be collapsible at all (unless overidden in the form definition).
+ if (method_exists($renderer, 'setCollapsibleElements') && !$this->_disableShortforms) {
+
+ // Count the number of sections.
+ $headerscount = 0;
+ foreach (array_keys($this->_elements) as $elementIndex){
+ $element =& $this->_elements[$elementIndex];
+ if ($element->getType() == 'header') {
+ $headerscount++;
+ }
+ }
+
+ $anyrequiredorerror = false;
$headercounter = 0;
+ $headername = null;
foreach (array_keys($this->_elements) as $elementIndex){
$element =& $this->_elements[$elementIndex];
+
if ($element->getType() == 'header') {
$headercounter++;
+ $element->_generateId();
+ $headername = $element->getName();
+ $anyrequiredorerror = false;
+ } else if (in_array($element->getName(), $this->_required) || isset($this->_errors[$element->getName()])) {
+ $anyrequiredorerror = true;
+ } else {
+ // Do not reset $anyrequiredorerror to false because we do not want any other element
+ // in this header (fieldset) to possibly revert the state given.
}
- }
- if ($headercounter > $this->_non_collapsible_headers) {
- // So, we have more than $_non_collapsible_headers headers
- // add all headers to collapsible elements array (if they have not been added yet).
- $anyrequiredorerror = false;
- $headercounter = 0;
- $headername = null;
- foreach (array_keys($this->_elements) as $elementIndex){
- $element =& $this->_elements[$elementIndex];
-
- if ($element->getType() == 'header') {
- $headercounter++;
- $element->_generateId();
- $headername = $element->getName();
- $anyrequiredorerror = false;
- } else if (in_array($element->getName(), $this->_required) || isset($this->_errors[$element->getName()])) {
- $anyrequiredorerror = true;
- }
- if ($headercounter === 1 || $anyrequiredorerror) {
- // If we're working on the first header, or if any error or required field
- // is present in this header, we need to expand it.
+ if ($element->getType() == 'header') {
+ if ($headercounter === 1 && !isset($this->_collapsibleElements[$headername])) {
+ // By default the first section is always expanded, except if a state has already been set.
+ $this->setExpanded($headername, true);
+ } else if (($headercounter === 2 && $headerscount === 2) && !isset($this->_collapsibleElements[$headername])) {
+ // The second section is always expanded if the form only contains 2 sections),
+ // except if a state has already been set.
$this->setExpanded($headername, true);
- } else if (!isset($this->_collapsibleElements[$headername])) {
- // Define element as collapsed by default.
- $this->setExpanded($headername, false);
}
+ } else if ($anyrequiredorerror) {
+ // If any error or required field are present within the header, we need to expand it.
+ $this->setExpanded($headername, true, true);
+ } else if (!isset($this->_collapsibleElements[$headername])) {
+ // Define element as collapsed by default.
+ $this->setExpanded($headername, false);
}
}
+
// Pass the array to renderer object.
$renderer->setCollapsibleElements($this->_collapsibleElements);
}

0 comments on commit 90a7e55

Please sign in to comment.