1(function ($) { 2 "use strict"; 3 4 var $openSelectivo; 5 var keyCode = { 6 enter: "13", 7 escape: "27", 8 up: "38", 9 down: "40", 10 }; 11 12 // Constructor 13 //-------------------- 14 $.fn.selectivo = function () { 15 init(this); 16 return this; 17 }; 18 19 function init($selectList) { 20 // Select the default option when loading the select box 21 $selectList.each(function () { 22 var $select = $(this); 23 var $option = $select.find(".selectivo__option:first-child"); 24 selectOption($select, $option); 25 }); 26 27 initToggle($selectList); 28 initFocus($selectList); 29 } 30 31 // Toggling 32 //-------------------- 33 function initToggle($selectList) { 34 // Toggle selectivo when the label is clicked 35 // Close selectivo & select option when an option is clicked 36 $selectList.on( 37 "click", 38 ".selectivo__label", 39 function (e) { 40 e.preventDefault(); 41 e.stopPropagation(); 42 var $select = $(this).parents(".selectivo"); 43 toggle($select); 44 return false; 45 } 46 ); 47 48 $selectList.on( 49 "click", 50 ".selectivo__option", 51 function (e) { 52 var $target = $(this); 53 var $select = $target.parents(".selectivo"); 54 selectOption($select, $target); 55 close($select); 56 } 57 ); 58 } 59 60 function toggle($select, state) { 61 if (typeof state === "undefined") { 62 state = !isOpen($select); 63 } 64 65 if (state) { 66 if ($openSelectivo && $openSelectivo !== $select) { 67 close($openSelectivo); 68 } 69 $openSelectivo = $select; 70 } else if ($openSelectivo === $select) { 71 $openSelectivo = null; 72 } 73 74 $select.toggleClass("selectivo--open", state); 75 toggleFocus($select, state); 76 } 77 78 function isOpen($select) { 79 return $select.hasClass("selectivo--open"); 80 } 81 82 function open($select) { 83 toggle($select, true); 84 } 85 86 function close($select) { 87 toggle($select, false); 88 } 89 90 // Selection 91 //-------------------- 92 function selectValue($select, label, value) { 93 if (label) { 94 if (typeof value == "undefined") { 95 value = label; 96 } 97 98 $select.find(".selectivo__input").val(value); 99 100 $select.find(".selectivo__label").html(label); 101 } 102 } 103 104 function selectOption($select, $option, event) { 105 var label = $option.html(); 106 var value = $option.val(); 107 selectValue($select, label, value); 108 109 $select 110 .find(".selectivo__option") 111 .removeClass("selectivo__option--selected"); 112 $option.addClass("selectivo__option--selected"); 113 } 114 115 // Focus 116 //-------------------- 117 function initFocus($selectList) { 118 // Close selectivo when escape pressed 119 // Open selectivo or navigate options when up/down arrows pressed 120 $selectList.on("keydown", function (event) { 121 if (event.keyCode == keyCode.enter) { 122 var $target = $(event.target); 123 if ($target.hasClass(".selectivo__option")) { 124 $target.click(); 125 return false; 126 } 127 } 128 129 if (event.keyCode == keyCode.escape) { 130 close($(this)); 131 return; 132 } 133 134 if (event.keyCode == keyCode.up || event.keyCode == keyCode.down) { 135 var $select = $(this); 136 if (!isOpen($select)) { 137 open($select); 138 } else { 139 if (event.keyCode == keyCode.up) { 140 focusPreviousElement($select); 141 } else { 142 focusNextElement($select); 143 } 144 } 145 146 return false; 147 } 148 }); 149 150 // Close selectivo when clicking outside 151 $(document).on("click", function (event) { 152 if ($openSelectivo) { 153 var $target = $(event.target); 154 if (!$target.closest(".selectivo").length) { 155 close($openSelectivo); 156 } 157 } 158 }); 159 } 160 161 function toggleFocus($select, state) { 162 var $label = $select.find("> .selectivo__label"); 163 if (state) { 164 focusCurrentOption($select); 165 $label.attr("tabindex", "-1"); 166 } else { 167 $label.removeAttr("tabindex"); 168 if (isFocusIn($select)) { 169 $label.focus(); 170 } 171 } 172 } 173 174 function getFocusableElements($select) { 175 return $select 176 .find(".selectivo__label, .selectivo__option, :focus") 177 .not("[tabindex=-1], [disabled], :hidden"); 178 } 179 180 function focusNextElement($select) { 181 var $elementList = getFocusableElements($select); 182 $elementList.eq($elementList.index($select.find(":focus")) + 1).focus(); 183 } 184 185 function focusPreviousElement($select) { 186 var $elementList = getFocusableElements($select); 187 $elementList 188 .eq(Math.max(0, $elementList.index($select.find(":focus")) - 1)) 189 .focus(); 190 } 191 192 function focusCurrentOption($select) { 193 console.log( 194 findOr( 195 $select, 196 ".selectivo__option--selected", 197 ".selectivo__option" 198 ).first() 199 ); 200 findOr($select, ".selectivo__option--selected", ".selectivo__option") 201 .first() 202 .focus(); 203 } 204 205 function isFocusIn($select) { 206 return !!$select.find(":focus").length; 207 } 208 209 // Utils 210 //-------------------- 211 function findOr(context, selector) { 212 var selectorList = Array.prototype.slice.call(arguments, 1); 213 for (var i = 0; i < selectorList.length; i++) { 214 var $found = $(context).find(selectorList[i]); 215 if ($found.length > 0) {
216 return $found; 217 } 218 } 219 220 return $(); 221 } 222})(jQuery);
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.