form_example_states.inc 9.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296
  1. <?php
  2. /**
  3. * @file
  4. * An example of how to use the new #states Form API element, allowing
  5. * dynamic form behavior with very simple setup.
  6. */
  7. /**
  8. * States demo form.
  9. *
  10. * This form shows off the #states system by dynamically showing parts of the
  11. * form based on the state of other parts.
  12. *
  13. * @ingroup form_example
  14. *
  15. * The basic idea is that you add a #states property to the element which is
  16. * to be changed based on some action elsewhere on the form. The #states
  17. * property lists a change which is to be made, and under what conditions
  18. * that change should be made.
  19. *
  20. * For example, in the 'tests_taken' form element below we have:
  21. * @code
  22. * '#states' => array(
  23. * 'visible' => array(
  24. * ':input[name="student_type"]' => array('value' => 'high_school'),
  25. * ),
  26. * ),
  27. * @endcode
  28. * Meaning that the element is to be made visible when the condition is met.
  29. * The condition is a combination of a jQuery selector (which selects the
  30. * element we want to test) and a condition for that element. In this case,
  31. * the condition is whether the return value of the 'student_type' element is
  32. * 'high_school'. If it is, this element will be visible.
  33. *
  34. * So the syntax is:
  35. * @code
  36. * '#states' => array(
  37. * 'action_to_take_on_this_form_element' => array(
  38. * 'jquery_selector_for_another_element' => array(
  39. * 'condition_type' => value,
  40. * ),
  41. * ),
  42. * ),
  43. * @endcode
  44. *
  45. * If you need an action to take place only when two different conditions are
  46. * true, then you add both of those conditions to the action. See the
  47. * 'country_writein' element below for an example.
  48. *
  49. * Note that the easiest way to select a textfield, checkbox, or select is with
  50. * the
  51. * @link http://api.jquery.com/input-selector/ ':input' jquery shortcut @endlink,
  52. * which selects any any of those.
  53. *
  54. * There are examples below of changing or hiding an element when a checkbox
  55. * is checked, when a textarea is filled, when a select has a given value.
  56. *
  57. * See drupal_process_states() for full documentation.
  58. *
  59. * @see forms_api_reference.html
  60. */
  61. function form_example_states_form($form, &$form_state) {
  62. $form['student_type'] = array(
  63. '#type' => 'radios',
  64. '#options' => array(
  65. 'high_school' => t('High School'),
  66. 'undergraduate' => t('Undergraduate'),
  67. 'graduate' => t('Graduate'),
  68. ),
  69. '#title' => t('What type of student are you?'),
  70. );
  71. $form['high_school'] = array(
  72. '#type' => 'fieldset',
  73. '#title' => t('High School Information'),
  74. // This #states rule says that the "high school" fieldset should only
  75. // be shown if the "student_type" form element is set to "High School".
  76. '#states' => array(
  77. 'visible' => array(
  78. ':input[name="student_type"]' => array('value' => 'high_school'),
  79. ),
  80. ),
  81. );
  82. // High school information.
  83. $form['high_school']['tests_taken'] = array(
  84. '#type' => 'checkboxes',
  85. '#options' => drupal_map_assoc(array(t('SAT'), t('ACT'))),
  86. '#title' => t('What standardized tests did you take?'),
  87. // This #states rule says that this checkboxes array will be visible only
  88. // when $form['student_type'] is set to t('High School').
  89. // It uses the jQuery selector :input[name=student_type] to choose the
  90. // element which triggers the behavior, and then defines the "High School"
  91. // value as the one that triggers visibility.
  92. '#states' => array(
  93. // Action to take.
  94. 'visible' => array(
  95. ':input[name="student_type"]' => array('value' => 'high_school'),
  96. ),
  97. ),
  98. );
  99. $form['high_school']['sat_score'] = array(
  100. '#type' => 'textfield',
  101. '#title' => t('Your SAT score:'),
  102. '#size' => 4,
  103. // This #states rule limits visibility to when the $form['tests_taken']
  104. // 'SAT' checkbox is checked."
  105. '#states' => array(
  106. // Action to take.
  107. 'visible' => array(
  108. ':input[name="tests_taken[SAT]"]' => array('checked' => TRUE),
  109. ),
  110. ),
  111. );
  112. $form['high_school']['act_score'] = array(
  113. '#type' => 'textfield',
  114. '#title' => t('Your ACT score:'),
  115. '#size' => 4,
  116. // Set this element visible if the ACT checkbox above is checked.
  117. '#states' => array(
  118. // Action to take.
  119. 'visible' => array(
  120. ':input[name="tests_taken[ACT]"]' => array('checked' => TRUE),
  121. ),
  122. ),
  123. );
  124. // Undergrad information.
  125. $form['undergraduate'] = array(
  126. '#type' => 'fieldset',
  127. '#title' => t('Undergraduate Information'),
  128. // This #states rule says that the "undergraduate" fieldset should only
  129. // be shown if the "student_type" form element is set to "Undergraduate".
  130. '#states' => array(
  131. 'visible' => array(
  132. ':input[name="student_type"]' => array('value' => 'undergraduate'),
  133. ),
  134. ),
  135. );
  136. $form['undergraduate']['how_many_years'] = array(
  137. '#type' => 'select',
  138. '#title' => t('How many years have you completed?'),
  139. // The options here are integers, but since all the action here happens
  140. // using the DOM on the client, we will have to use strings to work with
  141. // them.
  142. '#options' => array(
  143. 1 => t('One'),
  144. 2 => t('Two'),
  145. 3 => t('Three'),
  146. 4 => t('Four'),
  147. 5 => t('Lots'),
  148. ),
  149. );
  150. $form['undergraduate']['comment'] = array(
  151. '#type' => 'item',
  152. '#description' => t("Wow, that's a long time."),
  153. '#states' => array(
  154. 'visible' => array(
  155. // Note that '5' must be used here instead of the integer 5.
  156. // The information is coming from the DOM as a string.
  157. ':input[name="how_many_years"]' => array('value' => '5'),
  158. ),
  159. ),
  160. );
  161. $form['undergraduate']['school_name'] = array(
  162. '#type' => 'textfield',
  163. '#title' => t('Your college or university:'),
  164. );
  165. $form['undergraduate']['school_country'] = array(
  166. '#type' => 'select',
  167. '#options' => drupal_map_assoc(array(t('UK'), t('Other'))),
  168. '#title' => t('In what country is your college or university located?'),
  169. );
  170. $form['undergraduate']['country_writein'] = array(
  171. '#type' => 'textfield',
  172. '#size' => 20,
  173. '#title' => t('Please enter the name of the country where your college or university is located.'),
  174. // Only show this field if school_country is set to 'Other'.
  175. '#states' => array(
  176. // Action to take: Make visible.
  177. 'visible' => array(
  178. ':input[name="school_country"]' => array('value' => t('Other')),
  179. ),
  180. ),
  181. );
  182. $form['undergraduate']['thanks'] = array(
  183. '#type' => 'item',
  184. '#description' => t('Thanks for providing both your school and your country.'),
  185. '#states' => array(
  186. // Here visibility requires that two separate conditions be true.
  187. 'visible' => array(
  188. ':input[name="school_country"]' => array('value' => t('Other')),
  189. ':input[name="country_writein"]' => array('filled' => TRUE),
  190. ),
  191. ),
  192. );
  193. $form['undergraduate']['go_away'] = array(
  194. '#type' => 'submit',
  195. '#value' => t('Done with form'),
  196. '#states' => array(
  197. // Here visibility requires that two separate conditions be true.
  198. 'visible' => array(
  199. ':input[name="school_country"]' => array('value' => t('Other')),
  200. ':input[name="country_writein"]' => array('filled' => TRUE),
  201. ),
  202. ),
  203. );
  204. // Graduate student information.
  205. $form['graduate'] = array(
  206. '#type' => 'fieldset',
  207. '#title' => t('Graduate School Information'),
  208. // This #states rule says that the "graduate" fieldset should only
  209. // be shown if the "student_type" form element is set to "Graduate".
  210. '#states' => array(
  211. 'visible' => array(
  212. ':input[name="student_type"]' => array('value' => 'graduate'),
  213. ),
  214. ),
  215. );
  216. $form['graduate']['more_info'] = array(
  217. '#type' => 'textarea',
  218. '#title' => t('Please describe your graduate studies'),
  219. );
  220. $form['graduate']['info_provide'] = array(
  221. '#type' => 'checkbox',
  222. '#title' => t('Check here if you have provided information above'),
  223. '#disabled' => TRUE,
  224. '#states' => array(
  225. // Mark this checkbox checked if the "more_info" textarea has something
  226. // in it, if it's 'filled'.
  227. 'checked' => array(
  228. ':input[name="more_info"]' => array('filled' => TRUE),
  229. ),
  230. ),
  231. );
  232. $form['average'] = array(
  233. '#type' => 'textfield',
  234. '#title' => t('Enter your average'),
  235. // To trigger a state when the same controlling element can have more than
  236. // one possible value, put all values in a higher-level array.
  237. '#states' => array(
  238. 'visible' => array(
  239. ':input[name="student_type"]' => array(
  240. array('value' => 'high_school'),
  241. array('value' => 'undergraduate'),
  242. ),
  243. ),
  244. ),
  245. );
  246. $form['expand_more_info'] = array(
  247. '#type' => 'checkbox',
  248. '#title' => t('Check here if you want to add more information.'),
  249. );
  250. $form['more_info'] = array(
  251. '#type' => 'fieldset',
  252. '#title' => t('Additional Information'),
  253. '#collapsible' => TRUE,
  254. '#collapsed' => TRUE,
  255. // Expand the expand_more_info fieldset if the box is checked.
  256. '#states' => array(
  257. 'expanded' => array(
  258. ':input[name="expand_more_info"]' => array('checked' => TRUE),
  259. ),
  260. ),
  261. );
  262. $form['more_info']['feedback'] = array(
  263. '#type' => 'textarea',
  264. '#title' => t('What do you have to say?'),
  265. );
  266. $form['submit'] = array(
  267. '#type' => 'submit',
  268. '#value' => t('Submit your information'),
  269. );
  270. return $form;
  271. }
  272. /**
  273. * Submit handler for form_example_states_form().
  274. */
  275. function form_example_states_form_submit($form, &$form_state) {
  276. drupal_set_message(t('Submitting values: @values', array('@values' => var_export($form_state['values'], TRUE))));
  277. }