You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

288 lines
7.4 KiB

1 year ago
  1. /*!
  2. * jQuery UI Checkboxradio 1.13.2
  3. * http://jqueryui.com
  4. *
  5. * Copyright jQuery Foundation and other contributors
  6. * Released under the MIT license.
  7. * http://jquery.org/license
  8. */
  9. //>>label: Checkboxradio
  10. //>>group: Widgets
  11. //>>description: Enhances a form with multiple themeable checkboxes or radio buttons.
  12. //>>docs: http://api.jqueryui.com/checkboxradio/
  13. //>>demos: http://jqueryui.com/checkboxradio/
  14. //>>css.structure: ../../themes/base/core.css
  15. //>>css.structure: ../../themes/base/button.css
  16. //>>css.structure: ../../themes/base/checkboxradio.css
  17. //>>css.theme: ../../themes/base/theme.css
  18. ( function( factory ) {
  19. "use strict";
  20. if ( typeof define === "function" && define.amd ) {
  21. // AMD. Register as an anonymous module.
  22. define( [
  23. "jquery",
  24. "./core"
  25. ], factory );
  26. } else {
  27. // Browser globals
  28. factory( jQuery );
  29. }
  30. } )( function( $ ) {
  31. "use strict";
  32. $.widget( "ui.checkboxradio", [ $.ui.formResetMixin, {
  33. version: "1.13.2",
  34. options: {
  35. disabled: null,
  36. label: null,
  37. icon: true,
  38. classes: {
  39. "ui-checkboxradio-label": "ui-corner-all",
  40. "ui-checkboxradio-icon": "ui-corner-all"
  41. }
  42. },
  43. _getCreateOptions: function() {
  44. var disabled, labels, labelContents;
  45. var options = this._super() || {};
  46. // We read the type here, because it makes more sense to throw a element type error first,
  47. // rather then the error for lack of a label. Often if its the wrong type, it
  48. // won't have a label (e.g. calling on a div, btn, etc)
  49. this._readType();
  50. labels = this.element.labels();
  51. // If there are multiple labels, use the last one
  52. this.label = $( labels[ labels.length - 1 ] );
  53. if ( !this.label.length ) {
  54. $.error( "No label found for checkboxradio widget" );
  55. }
  56. this.originalLabel = "";
  57. // We need to get the label text but this may also need to make sure it does not contain the
  58. // input itself.
  59. // The label contents could be text, html, or a mix. We wrap all elements
  60. // and read the wrapper's `innerHTML` to get a string representation of
  61. // the label, without the input as part of it.
  62. labelContents = this.label.contents().not( this.element[ 0 ] );
  63. if ( labelContents.length ) {
  64. this.originalLabel += labelContents
  65. .clone()
  66. .wrapAll( "<div></div>" )
  67. .parent()
  68. .html();
  69. }
  70. // Set the label option if we found label text
  71. if ( this.originalLabel ) {
  72. options.label = this.originalLabel;
  73. }
  74. disabled = this.element[ 0 ].disabled;
  75. if ( disabled != null ) {
  76. options.disabled = disabled;
  77. }
  78. return options;
  79. },
  80. _create: function() {
  81. var checked = this.element[ 0 ].checked;
  82. this._bindFormResetHandler();
  83. if ( this.options.disabled == null ) {
  84. this.options.disabled = this.element[ 0 ].disabled;
  85. }
  86. this._setOption( "disabled", this.options.disabled );
  87. this._addClass( "ui-checkboxradio", "ui-helper-hidden-accessible" );
  88. this._addClass( this.label, "ui-checkboxradio-label", "ui-button ui-widget" );
  89. if ( this.type === "radio" ) {
  90. this._addClass( this.label, "ui-checkboxradio-radio-label" );
  91. }
  92. if ( this.options.label && this.options.label !== this.originalLabel ) {
  93. this._updateLabel();
  94. } else if ( this.originalLabel ) {
  95. this.options.label = this.originalLabel;
  96. }
  97. this._enhance();
  98. if ( checked ) {
  99. this._addClass( this.label, "ui-checkboxradio-checked", "ui-state-active" );
  100. }
  101. this._on( {
  102. change: "_toggleClasses",
  103. focus: function() {
  104. this._addClass( this.label, null, "ui-state-focus ui-visual-focus" );
  105. },
  106. blur: function() {
  107. this._removeClass( this.label, null, "ui-state-focus ui-visual-focus" );
  108. }
  109. } );
  110. },
  111. _readType: function() {
  112. var nodeName = this.element[ 0 ].nodeName.toLowerCase();
  113. this.type = this.element[ 0 ].type;
  114. if ( nodeName !== "input" || !/radio|checkbox/.test( this.type ) ) {
  115. $.error( "Can't create checkboxradio on element.nodeName=" + nodeName +
  116. " and element.type=" + this.type );
  117. }
  118. },
  119. // Support jQuery Mobile enhanced option
  120. _enhance: function() {
  121. this._updateIcon( this.element[ 0 ].checked );
  122. },
  123. widget: function() {
  124. return this.label;
  125. },
  126. _getRadioGroup: function() {
  127. var group;
  128. var name = this.element[ 0 ].name;
  129. var nameSelector = "input[name='" + $.escapeSelector( name ) + "']";
  130. if ( !name ) {
  131. return $( [] );
  132. }
  133. if ( this.form.length ) {
  134. group = $( this.form[ 0 ].elements ).filter( nameSelector );
  135. } else {
  136. // Not inside a form, check all inputs that also are not inside a form
  137. group = $( nameSelector ).filter( function() {
  138. return $( this )._form().length === 0;
  139. } );
  140. }
  141. return group.not( this.element );
  142. },
  143. _toggleClasses: function() {
  144. var checked = this.element[ 0 ].checked;
  145. this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );
  146. if ( this.options.icon && this.type === "checkbox" ) {
  147. this._toggleClass( this.icon, null, "ui-icon-check ui-state-checked", checked )
  148. ._toggleClass( this.icon, null, "ui-icon-blank", !checked );
  149. }
  150. if ( this.type === "radio" ) {
  151. this._getRadioGroup()
  152. .each( function() {
  153. var instance = $( this ).checkboxradio( "instance" );
  154. if ( instance ) {
  155. instance._removeClass( instance.label,
  156. "ui-checkboxradio-checked", "ui-state-active" );
  157. }
  158. } );
  159. }
  160. },
  161. _destroy: function() {
  162. this._unbindFormResetHandler();
  163. if ( this.icon ) {
  164. this.icon.remove();
  165. this.iconSpace.remove();
  166. }
  167. },
  168. _setOption: function( key, value ) {
  169. // We don't allow the value to be set to nothing
  170. if ( key === "label" && !value ) {
  171. return;
  172. }
  173. this._super( key, value );
  174. if ( key === "disabled" ) {
  175. this._toggleClass( this.label, null, "ui-state-disabled", value );
  176. this.element[ 0 ].disabled = value;
  177. // Don't refresh when setting disabled
  178. return;
  179. }
  180. this.refresh();
  181. },
  182. _updateIcon: function( checked ) {
  183. var toAdd = "ui-icon ui-icon-background ";
  184. if ( this.options.icon ) {
  185. if ( !this.icon ) {
  186. this.icon = $( "<span>" );
  187. this.iconSpace = $( "<span> </span>" );
  188. this._addClass( this.iconSpace, "ui-checkboxradio-icon-space" );
  189. }
  190. if ( this.type === "checkbox" ) {
  191. toAdd += checked ? "ui-icon-check ui-state-checked" : "ui-icon-blank";
  192. this._removeClass( this.icon, null, checked ? "ui-icon-blank" : "ui-icon-check" );
  193. } else {
  194. toAdd += "ui-icon-blank";
  195. }
  196. this._addClass( this.icon, "ui-checkboxradio-icon", toAdd );
  197. if ( !checked ) {
  198. this._removeClass( this.icon, null, "ui-icon-check ui-state-checked" );
  199. }
  200. this.icon.prependTo( this.label ).after( this.iconSpace );
  201. } else if ( this.icon !== undefined ) {
  202. this.icon.remove();
  203. this.iconSpace.remove();
  204. delete this.icon;
  205. }
  206. },
  207. _updateLabel: function() {
  208. // Remove the contents of the label ( minus the icon, icon space, and input )
  209. var contents = this.label.contents().not( this.element[ 0 ] );
  210. if ( this.icon ) {
  211. contents = contents.not( this.icon[ 0 ] );
  212. }
  213. if ( this.iconSpace ) {
  214. contents = contents.not( this.iconSpace[ 0 ] );
  215. }
  216. contents.remove();
  217. this.label.append( this.options.label );
  218. },
  219. refresh: function() {
  220. var checked = this.element[ 0 ].checked,
  221. isDisabled = this.element[ 0 ].disabled;
  222. this._updateIcon( checked );
  223. this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );
  224. if ( this.options.label !== null ) {
  225. this._updateLabel();
  226. }
  227. if ( isDisabled !== this.options.disabled ) {
  228. this._setOptions( { "disabled": isDisabled } );
  229. }
  230. }
  231. } ] );
  232. return $.ui.checkboxradio;
  233. } );