select2-rails 3.5.4 → 3.5.5

Sign up to get free protection for your applications and to get access to all the features.
Files changed (47) hide show
  1. checksums.yaml +13 -5
  2. data/README.md +2 -2
  3. data/app/assets/javascripts/select2.js +232 -90
  4. data/app/assets/javascripts/select2_locale_ar.js +8 -8
  5. data/app/assets/javascripts/select2_locale_bg.js +8 -7
  6. data/app/assets/javascripts/select2_locale_ca.js +2 -2
  7. data/app/assets/javascripts/select2_locale_cs.js +2 -2
  8. data/app/assets/javascripts/select2_locale_de.js +2 -2
  9. data/app/assets/javascripts/select2_locale_el.js +7 -7
  10. data/app/assets/javascripts/select2_locale_es.js +4 -4
  11. data/app/assets/javascripts/select2_locale_eu.js +2 -2
  12. data/app/assets/javascripts/select2_locale_fa.js +7 -5
  13. data/app/assets/javascripts/select2_locale_fi.js +2 -2
  14. data/app/assets/javascripts/select2_locale_fr.js +2 -2
  15. data/app/assets/javascripts/select2_locale_gl.js +2 -2
  16. data/app/assets/javascripts/select2_locale_he.js +2 -2
  17. data/app/assets/javascripts/select2_locale_hr.js +10 -30
  18. data/app/assets/javascripts/select2_locale_hu.js +3 -3
  19. data/app/assets/javascripts/select2_locale_id.js +2 -2
  20. data/app/assets/javascripts/select2_locale_is.js +4 -5
  21. data/app/assets/javascripts/select2_locale_it.js +2 -2
  22. data/app/assets/javascripts/select2_locale_ko.js +2 -2
  23. data/app/assets/javascripts/select2_locale_lt.js +12 -17
  24. data/app/assets/javascripts/select2_locale_lv.js +8 -7
  25. data/app/assets/javascripts/select2_locale_mk.js +2 -2
  26. data/app/assets/javascripts/select2_locale_ms.js +2 -2
  27. data/app/assets/javascripts/select2_locale_nl.js +2 -2
  28. data/app/assets/javascripts/select2_locale_no.js +2 -2
  29. data/app/assets/javascripts/select2_locale_pl.js +13 -28
  30. data/app/assets/javascripts/select2_locale_pt-BR.js +2 -2
  31. data/app/assets/javascripts/select2_locale_pt-PT.js +2 -2
  32. data/app/assets/javascripts/select2_locale_ro.js +2 -2
  33. data/app/assets/javascripts/select2_locale_rs.js +17 -0
  34. data/app/assets/javascripts/select2_locale_ru.js +12 -6
  35. data/app/assets/javascripts/select2_locale_sk.js +2 -2
  36. data/app/assets/javascripts/select2_locale_sv.js +2 -2
  37. data/app/assets/javascripts/select2_locale_th.js +2 -2
  38. data/app/assets/javascripts/select2_locale_tr.js +2 -2
  39. data/app/assets/javascripts/select2_locale_uk.js +12 -7
  40. data/app/assets/javascripts/select2_locale_vi.js +2 -2
  41. data/app/assets/javascripts/select2_locale_zh-CN.js +2 -2
  42. data/app/assets/javascripts/select2_locale_zh-TW.js +2 -2
  43. data/app/assets/stylesheets/select2-bootstrap.css +1 -1
  44. data/app/assets/stylesheets/select2.css.erb +60 -29
  45. data/lib/select2-rails/source_file.rb +1 -1
  46. data/lib/select2-rails/version.rb +1 -1
  47. metadata +8 -8
checksums.yaml CHANGED
@@ -1,7 +1,15 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: e3f7b9a99c762dedfa76ab00bce7f13060632ca6
4
- data.tar.gz: e5682bb1caef623ac6613d8fc252680fe81ec332
2
+ !binary "U0hBMQ==":
3
+ metadata.gz: !binary |-
4
+ NTQ5NjljNGNiNmFjZjdiMmJhYmRjYzA5YzM1NGI2MDk1ZmJhMmVjNw==
5
+ data.tar.gz: !binary |-
6
+ ODQ1M2Q1ZmFlZGY4ZDI2ZTI5NTlmNjM2Y2ZhOGI2NmYxNjJhNDBhOA==
5
7
  SHA512:
6
- metadata.gz: 7929bfc1e29f1cf3c782363ca3d1951b67467c6f9beac94763a3d4d58187d7c43e8b7b966fc007e5b91767e428c67fcc0493e5b7d1763ab007c385d560ca2bee
7
- data.tar.gz: 3559db642b5b4fb60765239ce37330b49764ebc893710b217ea9277f5ae9a19f6fb326113d4d2d3b28e2e658016e0e3902dc4889046d56c107e84d3fb2820651
8
+ metadata.gz: !binary |-
9
+ YzEwZDVkYzlkYmI1YThiMDMwMWI1NDBiOWM5MDY2ZGZlM2YzYzhhMGQ2Yjky
10
+ NTk3ZTNhNzg1MWIyYzU1NDljMjVkN2EyNGZjMWRmMzczZGUyYTBjOGY0Y2Iz
11
+ OTk3YmU0Y2YwMWMzNmYwZTdkYTJjYmUzZjMxYzA4MzE0Zjg1OTQ=
12
+ data.tar.gz: !binary |-
13
+ NGVlNDAwNzc1NTVlOTIxNzE2YzliMzZmMzUzNjY1MTQ2YWVjMmFkOGE5NjAx
14
+ M2MzMTc2YTA3MGFjYzg5ODkzYWQ1Zjc2YWI1MzgzYzI2MWRjNDYzOWQ3YTBh
15
+ MjZiMzgzM2Y0OWExMzI0ZWRlYzMyZjI0YTVkMzkzODgzYzYxZjI=
data/README.md CHANGED
@@ -26,7 +26,7 @@ Add to your `app/assets/stylesheets/application.css`:
26
26
 
27
27
  *= require select2
28
28
 
29
- If you are using Twitter Boostrap you can require ethe bootstrap theme CSS
29
+ If you are using Twitter Boostrap you need to also require the bootstrap theme CSS in addition to the above require.
30
30
 
31
31
  *= require select2-bootstrap
32
32
 
@@ -40,7 +40,7 @@ Add the following to your `app/assets/javascripts/application.js`:
40
40
 
41
41
  Possible languages:
42
42
 
43
- ar, ca, cs, da, de, el, es, et, eu, fi, fr, gl, he, hr, hu, id, is, it, ja, ko, lt, lv, mk, ms, nl, no, pl, pt-BR, pt-PT, ro, ru, sk, sv, tr, uk, vi, zh-CN, zh-TW
43
+ ar, ca, cs, da, de, el, es, et, eu, fi, fr, gl, he, hr, hu, id, is, it, ja, ko, lt, lv, mk, ms, nl, no, pl, pt-BR, pt-PT, ro, rs, ru, sk, sv, tr, uk, vi, zh-CN, zh-TW
44
44
 
45
45
  ## Example
46
46
  Code [here](https://github.com/argerim/select_2_example)
@@ -1,7 +1,7 @@
1
1
  /*
2
2
  Copyright 2012 Igor Vaynberg
3
3
 
4
- Version: 3.4.5 Timestamp: Mon Nov 4 08:22:42 PST 2013
4
+ Version: 3.4.6 Timestamp: Sat Mar 22 22:30:15 EDT 2014
5
5
 
6
6
  This software is licensed under the Apache License, Version 2.0 (the "Apache License") or the GNU
7
7
  General Public License version 2 (the "GPL License"). You may choose either license to govern your
@@ -14,7 +14,7 @@ You may obtain a copy of the Apache License and the GPL License at:
14
14
  http://www.gnu.org/licenses/gpl-2.0.html
15
15
 
16
16
  Unless required by applicable law or agreed to in writing, software distributed under the
17
- Apache License or the GPL Licesnse is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
17
+ Apache License or the GPL License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
18
18
  CONDITIONS OF ANY KIND, either express or implied. See the Apache License and the GPL License for
19
19
  the specific language governing permissions and limitations under the Apache License and the GPL License.
20
20
  */
@@ -105,6 +105,14 @@ the specific language governing permissions and limitations under the Apache Lic
105
105
  nextUid=(function() { var counter=1; return function() { return counter++; }; }());
106
106
 
107
107
 
108
+ function reinsertElement(element) {
109
+ var placeholder = $(document.createTextNode(''));
110
+
111
+ element.before(placeholder);
112
+ placeholder.before(element);
113
+ placeholder.remove();
114
+ }
115
+
108
116
  function stripDiacritics(str) {
109
117
  var ret, i, l, c;
110
118
 
@@ -264,7 +272,8 @@ the specific language governing permissions and limitations under the Apache Lic
264
272
 
265
273
  /* make sure el received focus so we do not error out when trying to manipulate the caret.
266
274
  sometimes modals or others listeners may steal it after its set */
267
- if ($el.is(":visible") && el === document.activeElement) {
275
+ var isVisible = (el.offsetWidth > 0 || el.offsetHeight > 0);
276
+ if (isVisible && el === document.activeElement) {
268
277
 
269
278
  /* after the focus is set move the caret to the end, necessary when we val()
270
279
  just before setting focus */
@@ -393,12 +402,12 @@ the specific language governing permissions and limitations under the Apache Lic
393
402
  /**
394
403
  * Produces an ajax-based query function
395
404
  *
396
- * @param options object containing configuration paramters
405
+ * @param options object containing configuration parameters
397
406
  * @param options.params parameter map for the transport ajax call, can contain such options as cache, jsonpCallback, etc. see $.ajax
398
407
  * @param options.transport function that will be used to execute the ajax request. must be compatible with parameters supported by $.ajax
399
408
  * @param options.url url for the data
400
409
  * @param options.data a function(searchTerm, pageNumber, context) that should return an object containing query string parameters for the above url.
401
- * @param options.dataType request data type: ajax, jsonp, other datatatypes supported by jQuery's $.ajax function or the transport function if specified
410
+ * @param options.dataType request data type: ajax, jsonp, other datatypes supported by jQuery's $.ajax function or the transport function if specified
402
411
  * @param options.quietMillis (optional) milliseconds to wait before making the ajaxRequest, helps debounce the ajax function if invoked too often
403
412
  * @param options.results a function(remoteData, pageNumber) that converts data returned form the remote request to the format expected by Select2.
404
413
  * The expected format is an object containing the following keys:
@@ -431,7 +440,7 @@ the specific language governing permissions and limitations under the Apache Lic
431
440
  data = data ? data.call(self, query.term, query.page, query.context) : null;
432
441
  url = (typeof url === 'function') ? url.call(self, query.term, query.page, query.context) : url;
433
442
 
434
- if (handler) { handler.abort(); }
443
+ if (handler && typeof handler.abort === "function") { handler.abort(); }
435
444
 
436
445
  if (options.params) {
437
446
  if ($.isFunction(options.params)) {
@@ -555,11 +564,16 @@ the specific language governing permissions and limitations under the Apache Lic
555
564
  function checkFormatter(formatter, formatterName) {
556
565
  if ($.isFunction(formatter)) return true;
557
566
  if (!formatter) return false;
558
- throw new Error(formatterName +" must be a function or a falsy value");
567
+ if (typeof(formatter) === 'string') return true;
568
+ throw new Error(formatterName +" must be a string, function, or falsy value");
559
569
  }
560
570
 
561
571
  function evaluate(val) {
562
- return $.isFunction(val) ? val() : val;
572
+ if ($.isFunction(val)) {
573
+ var args = Array.prototype.slice.call(arguments, 1);
574
+ return val.apply(null, args);
575
+ }
576
+ return val;
563
577
  }
564
578
 
565
579
  function countResults(results) {
@@ -669,8 +683,15 @@ the specific language governing permissions and limitations under the Apache Lic
669
683
 
670
684
  this.container = this.createContainer();
671
685
 
672
- this.containerId="s2id_"+(opts.element.attr("id") || "autogen"+nextUid());
673
- this.containerSelector="#"+this.containerId.replace(/([;&,\.\+\*\~':"\!\^#$%@\[\]\(\)=>\|])/g, '\\$1');
686
+ this.liveRegion = $("<span>", {
687
+ role: "status",
688
+ "aria-live": "polite"
689
+ })
690
+ .addClass("select2-hidden-accessible")
691
+ .appendTo(document.body);
692
+
693
+ this.containerId="s2id_"+(opts.element.attr("id") || "autogen"+nextUid()).replace(/([;&,\-\.\+\*\~':"\!\^#$%@\[\]\(\)=>\|])/g, '\\$1');
694
+ this.containerSelector="#"+this.containerId;
674
695
  this.container.attr("id", this.containerId);
675
696
 
676
697
  // cache the body so future lookups are cheap
@@ -715,6 +736,9 @@ the specific language governing permissions and limitations under the Apache Lic
715
736
 
716
737
  installFilteredMouseMove(this.results);
717
738
  this.dropdown.on("mousemove-filtered touchstart touchmove touchend", resultsSelector, this.bind(this.highlightUnderEvent));
739
+ this.dropdown.on("touchend", resultsSelector, this.bind(this.selectHighlighted));
740
+ this.dropdown.on("touchmove", resultsSelector, this.bind(this.touchMoved));
741
+ this.dropdown.on("touchstart touchend", resultsSelector, this.bind(this.clearTouchMoved));
718
742
 
719
743
  installDebouncedScroll(80, this.results);
720
744
  this.dropdown.on("scroll-debounced", resultsSelector, this.bind(this.loadMoreIfNeeded));
@@ -752,7 +776,10 @@ the specific language governing permissions and limitations under the Apache Lic
752
776
  // trap all mouse events from leaving the dropdown. sometimes there may be a modal that is listening
753
777
  // for mouse events outside of itself so it can close itself. since the dropdown is now outside the select2's
754
778
  // dom it will trigger the popup close, which is not what we want
755
- this.dropdown.on("click mouseup mousedown", function (e) { e.stopPropagation(); });
779
+ // focusin can cause focus wars between modals and select2 since the dropdown is outside the modal.
780
+ this.dropdown.on("click mouseup mousedown focusin", function (e) { e.stopPropagation(); });
781
+
782
+ this.nextSearchTerm = undefined;
756
783
 
757
784
  if ($.isFunction(this.opts.initSelection)) {
758
785
  // initialize selection based on the current value of the source element
@@ -782,7 +809,7 @@ the specific language governing permissions and limitations under the Apache Lic
782
809
  opts.element.prop("autofocus", false);
783
810
  if (this.autofocus) this.focus();
784
811
 
785
- this.nextSearchTerm = undefined;
812
+ this.search.attr("placeholder", opts.searchInputPlaceholder);
786
813
  },
787
814
 
788
815
  // abstract
@@ -795,6 +822,7 @@ the specific language governing permissions and limitations under the Apache Lic
795
822
 
796
823
  if (select2 !== undefined) {
797
824
  select2.container.remove();
825
+ select2.liveRegion.remove();
798
826
  select2.dropdown.remove();
799
827
  element
800
828
  .removeClass("select2-offscreen")
@@ -852,7 +880,7 @@ the specific language governing permissions and limitations under the Apache Lic
852
880
 
853
881
  opts = $.extend({}, {
854
882
  populateResults: function(container, results, query) {
855
- var populate, id=this.opts.id;
883
+ var populate, id=this.opts.id, liveRegion=this.liveRegion;
856
884
 
857
885
  populate=function(results, container, depth) {
858
886
 
@@ -876,16 +904,19 @@ the specific language governing permissions and limitations under the Apache Lic
876
904
  if (disabled) { node.addClass("select2-disabled"); }
877
905
  if (compound) { node.addClass("select2-result-with-children"); }
878
906
  node.addClass(self.opts.formatResultCssClass(result));
907
+ node.attr("role", "presentation");
879
908
 
880
909
  label=$(document.createElement("div"));
881
910
  label.addClass("select2-result-label");
911
+ label.attr("id", "select2-result-label-" + nextUid());
912
+ label.attr("role", "option");
882
913
 
883
914
  formatted=opts.formatResult(result, label, query, self.opts.escapeMarkup);
884
915
  if (formatted!==undefined) {
885
916
  label.html(formatted);
917
+ node.append(label);
886
918
  }
887
919
 
888
- node.append(label);
889
920
 
890
921
  if (compound) {
891
922
 
@@ -898,6 +929,8 @@ the specific language governing permissions and limitations under the Apache Lic
898
929
  node.data("select2-data", result);
899
930
  container.append(node);
900
931
  }
932
+
933
+ liveRegion.text(opts.formatMatches(results.length));
901
934
  };
902
935
 
903
936
  populate(results, container, 0);
@@ -953,7 +986,6 @@ the specific language governing permissions and limitations under the Apache Lic
953
986
  });
954
987
  // this is needed because inside val() we construct choices from options and there id is hardcoded
955
988
  opts.id=function(e) { return e.id; };
956
- opts.formatResultCssClass = function(data) { return data.css; };
957
989
  } else {
958
990
  if (!("query" in opts)) {
959
991
 
@@ -991,6 +1023,16 @@ the specific language governing permissions and limitations under the Apache Lic
991
1023
  throw "query function not defined for Select2 " + opts.element.attr("id");
992
1024
  }
993
1025
 
1026
+ if (opts.createSearchChoicePosition === 'top') {
1027
+ opts.createSearchChoicePosition = function(list, item) { list.unshift(item); };
1028
+ }
1029
+ else if (opts.createSearchChoicePosition === 'bottom') {
1030
+ opts.createSearchChoicePosition = function(list, item) { list.push(item); };
1031
+ }
1032
+ else if (typeof(opts.createSearchChoicePosition) !== "function") {
1033
+ throw "invalid createSearchChoicePosition option must be 'top', 'bottom' or a custom function";
1034
+ }
1035
+
994
1036
  return opts;
995
1037
  },
996
1038
 
@@ -1069,7 +1111,7 @@ the specific language governing permissions and limitations under the Apache Lic
1069
1111
  // so here we trigger the click event manually
1070
1112
  this.opts.element.click();
1071
1113
 
1072
- // ValidationEngine ignorea the change event and listens instead to blur
1114
+ // ValidationEngine ignores the change event and listens instead to blur
1073
1115
  // so here we trigger the blur event manually if so desired
1074
1116
  if (this.opts.blurOnChange)
1075
1117
  this.opts.element.blur();
@@ -1113,12 +1155,11 @@ the specific language governing permissions and limitations under the Apache Lic
1113
1155
  // abstract
1114
1156
  readonly: function(enabled) {
1115
1157
  if (enabled === undefined) enabled = false;
1116
- if (this._readonly === enabled) return false;
1158
+ if (this._readonly === enabled) return;
1117
1159
  this._readonly = enabled;
1118
1160
 
1119
1161
  this.opts.element.prop("readonly", enabled);
1120
1162
  this.enableInterface();
1121
- return true;
1122
1163
  },
1123
1164
 
1124
1165
  // abstract
@@ -1141,7 +1182,7 @@ the specific language governing permissions and limitations under the Apache Lic
1141
1182
  dropTop = offset.top + height,
1142
1183
  dropLeft = offset.left,
1143
1184
  enoughRoomBelow = dropTop + dropHeight <= viewportBottom,
1144
- enoughRoomAbove = (offset.top - dropHeight) >= this.body().scrollTop(),
1185
+ enoughRoomAbove = (offset.top - dropHeight) >= $window.scrollTop(),
1145
1186
  dropWidth = $dropdown.outerWidth(false),
1146
1187
  enoughRoomOnRight = dropLeft + dropWidth <= viewPortRight,
1147
1188
  aboveNow = $dropdown.hasClass("select2-drop-above"),
@@ -1206,7 +1247,7 @@ the specific language governing permissions and limitations under the Apache Lic
1206
1247
  }
1207
1248
 
1208
1249
  if (!enoughRoomOnRight) {
1209
- dropLeft = offset.left + width - dropWidth;
1250
+ dropLeft = offset.left + this.container.outerWidth(false) - dropWidth;
1210
1251
  }
1211
1252
 
1212
1253
  css = {
@@ -1215,8 +1256,8 @@ the specific language governing permissions and limitations under the Apache Lic
1215
1256
  };
1216
1257
 
1217
1258
  if (above) {
1218
- css.bottom = windowHeight - offset.top;
1219
- css.top = 'auto';
1259
+ css.top = offset.top - dropHeight;
1260
+ css.bottom = 'auto';
1220
1261
  this.container.addClass("select2-drop-above");
1221
1262
  $dropdown.addClass("select2-drop-above");
1222
1263
  }
@@ -1286,7 +1327,7 @@ the specific language governing permissions and limitations under the Apache Lic
1286
1327
  this.dropdown.detach().appendTo(this.body());
1287
1328
  }
1288
1329
 
1289
- // create the dropdown mask if doesnt already exist
1330
+ // create the dropdown mask if doesn't already exist
1290
1331
  mask = $("#select2-drop-mask");
1291
1332
  if (mask.length == 0) {
1292
1333
  mask = $(document.createElement("div"));
@@ -1294,13 +1335,16 @@ the specific language governing permissions and limitations under the Apache Lic
1294
1335
  mask.hide();
1295
1336
  mask.appendTo(this.body());
1296
1337
  mask.on("mousedown touchstart click", function (e) {
1338
+ // Prevent IE from generating a click event on the body
1339
+ reinsertElement(mask);
1340
+
1297
1341
  var dropdown = $("#select2-drop"), self;
1298
1342
  if (dropdown.length > 0) {
1299
1343
  self=dropdown.data("select2");
1300
1344
  if (self.opts.selectOnBlur) {
1301
1345
  self.selectHighlighted({noFocus: true});
1302
1346
  }
1303
- self.close({focus:true});
1347
+ self.close();
1304
1348
  e.preventDefault();
1305
1349
  e.stopPropagation();
1306
1350
  }
@@ -1429,7 +1473,7 @@ the specific language governing permissions and limitations under the Apache Lic
1429
1473
 
1430
1474
  // abstract
1431
1475
  findHighlightableChoices: function() {
1432
- return this.results.find(".select2-result-selectable:not(.select2-disabled, .select2-selected)");
1476
+ return this.results.find(".select2-result-selectable:not(.select2-disabled):not(.select2-selected)");
1433
1477
  },
1434
1478
 
1435
1479
  // abstract
@@ -1465,8 +1509,13 @@ the specific language governing permissions and limitations under the Apache Lic
1465
1509
  choice = $(choices[index]);
1466
1510
  choice.addClass("select2-highlighted");
1467
1511
 
1512
+ // ensure assistive technology can determine the active choice
1513
+ this.search.attr("aria-activedescendant", choice.find(".select2-result-label").attr("id"));
1514
+
1468
1515
  this.ensureHighlightVisible();
1469
1516
 
1517
+ this.liveRegion.text(choice.text());
1518
+
1470
1519
  data = choice.data("select2-data");
1471
1520
  if (data) {
1472
1521
  this.opts.element.trigger({ type: "select2-highlight", val: this.id(data), choice: data });
@@ -1477,6 +1526,14 @@ the specific language governing permissions and limitations under the Apache Lic
1477
1526
  this.results.find(".select2-highlighted").removeClass("select2-highlighted");
1478
1527
  },
1479
1528
 
1529
+ touchMoved: function() {
1530
+ this._touchMoved = true;
1531
+ },
1532
+
1533
+ clearTouchMoved: function() {
1534
+ this._touchMoved = false;
1535
+ },
1536
+
1480
1537
  // abstract
1481
1538
  countSelectableResults: function() {
1482
1539
  return this.findHighlightableChoices().length;
@@ -1525,7 +1582,7 @@ the specific language governing permissions and limitations under the Apache Lic
1525
1582
  self.postprocessResults(data, false, false);
1526
1583
 
1527
1584
  if (data.more===true) {
1528
- more.detach().appendTo(results).text(self.opts.formatLoadMore(page+1));
1585
+ more.detach().appendTo(results).text(evaluate(self.opts.formatLoadMore, page+1));
1529
1586
  window.setTimeout(function() { self.loadMoreIfNeeded(); }, 10);
1530
1587
  } else {
1531
1588
  more.remove();
@@ -1574,6 +1631,12 @@ the specific language governing permissions and limitations under the Apache Lic
1574
1631
  function postRender() {
1575
1632
  search.removeClass("select2-active");
1576
1633
  self.positionDropdown();
1634
+ if (results.find('.select2-no-results,.select2-selection-limit,.select2-searching').length) {
1635
+ self.liveRegion.text(results.text());
1636
+ }
1637
+ else {
1638
+ self.liveRegion.text(self.opts.formatMatches(results.find('.select2-result-selectable').length));
1639
+ }
1577
1640
  }
1578
1641
 
1579
1642
  function render(html) {
@@ -1587,14 +1650,14 @@ the specific language governing permissions and limitations under the Apache Lic
1587
1650
  if (maxSelSize >=1) {
1588
1651
  data = this.data();
1589
1652
  if ($.isArray(data) && data.length >= maxSelSize && checkFormatter(opts.formatSelectionTooBig, "formatSelectionTooBig")) {
1590
- render("<li class='select2-selection-limit'>" + opts.formatSelectionTooBig(maxSelSize) + "</li>");
1653
+ render("<li class='select2-selection-limit'>" + evaluate(opts.formatSelectionTooBig, maxSelSize) + "</li>");
1591
1654
  return;
1592
1655
  }
1593
1656
  }
1594
1657
 
1595
1658
  if (search.val().length < opts.minimumInputLength) {
1596
1659
  if (checkFormatter(opts.formatInputTooShort, "formatInputTooShort")) {
1597
- render("<li class='select2-no-results'>" + opts.formatInputTooShort(search.val(), opts.minimumInputLength) + "</li>");
1660
+ render("<li class='select2-no-results'>" + evaluate(opts.formatInputTooShort, search.val(), opts.minimumInputLength) + "</li>");
1598
1661
  } else {
1599
1662
  render("");
1600
1663
  }
@@ -1604,7 +1667,7 @@ the specific language governing permissions and limitations under the Apache Lic
1604
1667
 
1605
1668
  if (opts.maximumInputLength && search.val().length > opts.maximumInputLength) {
1606
1669
  if (checkFormatter(opts.formatInputTooLong, "formatInputTooLong")) {
1607
- render("<li class='select2-no-results'>" + opts.formatInputTooLong(search.val(), opts.maximumInputLength) + "</li>");
1670
+ render("<li class='select2-no-results'>" + evaluate(opts.formatInputTooLong, search.val(), opts.maximumInputLength) + "</li>");
1608
1671
  } else {
1609
1672
  render("");
1610
1673
  }
@@ -1612,7 +1675,7 @@ the specific language governing permissions and limitations under the Apache Lic
1612
1675
  }
1613
1676
 
1614
1677
  if (opts.formatSearching && this.findHighlightableChoices().length === 0) {
1615
- render("<li class='select2-searching'>" + opts.formatSearching() + "</li>");
1678
+ render("<li class='select2-searching'>" + evaluate(opts.formatSearching) + "</li>");
1616
1679
  }
1617
1680
 
1618
1681
  search.addClass("select2-active");
@@ -1657,13 +1720,13 @@ the specific language governing permissions and limitations under the Apache Lic
1657
1720
  function () {
1658
1721
  return equal(self.id(this), self.id(def));
1659
1722
  }).length === 0) {
1660
- data.results.unshift(def);
1723
+ this.opts.createSearchChoicePosition(data.results, def);
1661
1724
  }
1662
1725
  }
1663
1726
  }
1664
1727
 
1665
1728
  if (data.results.length === 0 && checkFormatter(opts.formatNoMatches, "formatNoMatches")) {
1666
- render("<li class='select2-no-results'>" + opts.formatNoMatches(search.val()) + "</li>");
1729
+ render("<li class='select2-no-results'>" + evaluate(opts.formatNoMatches, search.val()) + "</li>");
1667
1730
  return;
1668
1731
  }
1669
1732
 
@@ -1671,7 +1734,7 @@ the specific language governing permissions and limitations under the Apache Lic
1671
1734
  self.opts.populateResults.call(this, results, data.results, {term: search.val(), page: this.resultsPage, context:null});
1672
1735
 
1673
1736
  if (data.more === true && checkFormatter(opts.formatLoadMore, "formatLoadMore")) {
1674
- results.append("<li class='select2-more-results'>" + self.opts.escapeMarkup(opts.formatLoadMore(this.resultsPage)) + "</li>");
1737
+ results.append("<li class='select2-more-results'>" + self.opts.escapeMarkup(evaluate(opts.formatLoadMore, this.resultsPage)) + "</li>");
1675
1738
  window.setTimeout(function() { self.loadMoreIfNeeded(); }, 10);
1676
1739
  }
1677
1740
 
@@ -1709,6 +1772,10 @@ the specific language governing permissions and limitations under the Apache Lic
1709
1772
 
1710
1773
  // abstract
1711
1774
  selectHighlighted: function (options) {
1775
+ if (this._touchMoved) {
1776
+ this.clearTouchMoved();
1777
+ return;
1778
+ }
1712
1779
  var index=this.highlight(),
1713
1780
  highlighted=this.results.find(".select2-highlighted"),
1714
1781
  data = highlighted.closest('.select2-result').data("select2-data");
@@ -1807,16 +1874,19 @@ the specific language governing permissions and limitations under the Apache Lic
1807
1874
  var container = $(document.createElement("div")).attr({
1808
1875
  "class": "select2-container"
1809
1876
  }).html([
1810
- "<a href='javascript:void(0)' onclick='return false;' class='select2-choice' tabindex='-1'>",
1877
+ "<a href='javascript:void(0)' class='select2-choice' tabindex='-1'>",
1811
1878
  " <span class='select2-chosen'>&nbsp;</span><abbr class='select2-search-choice-close'></abbr>",
1812
- " <span class='select2-arrow'><b></b></span>",
1879
+ " <span class='select2-arrow' role='presentation'><b role='presentation'></b></span>",
1813
1880
  "</a>",
1814
- "<input class='select2-focusser select2-offscreen' type='text'/>",
1881
+ "<label for='' class='select2-offscreen'></label>",
1882
+ "<input class='select2-focusser select2-offscreen' type='text' aria-haspopup='true' role='button' />",
1815
1883
  "<div class='select2-drop select2-display-none'>",
1816
1884
  " <div class='select2-search'>",
1817
- " <input type='text' autocomplete='off' autocorrect='off' autocapitalize='off' spellcheck='false' class='select2-input'/>",
1885
+ " <label for='' class='select2-offscreen'></label>",
1886
+ " <input type='text' autocomplete='off' autocorrect='off' autocapitalize='off' spellcheck='false' class='select2-input' role='combobox' aria-expanded='true'",
1887
+ " aria-autocomplete='list' />",
1818
1888
  " </div>",
1819
- " <ul class='select2-results'>",
1889
+ " <ul class='select2-results' role='listbox'>",
1820
1890
  " </ul>",
1821
1891
  "</div>"].join(""));
1822
1892
  return container;
@@ -1873,14 +1943,13 @@ the specific language governing permissions and limitations under the Apache Lic
1873
1943
  },
1874
1944
 
1875
1945
  // single
1876
- close: function (params) {
1946
+ close: function () {
1877
1947
  if (!this.opened()) return;
1878
1948
  this.parent.close.apply(this, arguments);
1879
1949
 
1880
- params = params || {focus: true};
1881
- this.focusser.removeAttr("disabled");
1950
+ this.focusser.prop("disabled", false);
1882
1951
 
1883
- if (params.focus) {
1952
+ if (this.opts.shouldFocusInput(this)) {
1884
1953
  this.focusser.focus();
1885
1954
  }
1886
1955
  },
@@ -1890,8 +1959,10 @@ the specific language governing permissions and limitations under the Apache Lic
1890
1959
  if (this.opened()) {
1891
1960
  this.close();
1892
1961
  } else {
1893
- this.focusser.removeAttr("disabled");
1894
- this.focusser.focus();
1962
+ this.focusser.prop("disabled", false);
1963
+ if (this.opts.shouldFocusInput(this)) {
1964
+ this.focusser.focus();
1965
+ }
1895
1966
  }
1896
1967
  },
1897
1968
 
@@ -1903,8 +1974,11 @@ the specific language governing permissions and limitations under the Apache Lic
1903
1974
  // single
1904
1975
  cancel: function () {
1905
1976
  this.parent.cancel.apply(this, arguments);
1906
- this.focusser.removeAttr("disabled");
1907
- this.focusser.focus();
1977
+ this.focusser.prop("disabled", false);
1978
+
1979
+ if (this.opts.shouldFocusInput(this)) {
1980
+ this.focusser.focus();
1981
+ }
1908
1982
  },
1909
1983
 
1910
1984
  // single
@@ -1919,7 +1993,9 @@ the specific language governing permissions and limitations under the Apache Lic
1919
1993
 
1920
1994
  var selection,
1921
1995
  container = this.container,
1922
- dropdown = this.dropdown;
1996
+ dropdown = this.dropdown,
1997
+ idSuffix = nextUid(),
1998
+ elementLabel;
1923
1999
 
1924
2000
  if (this.opts.minimumResultsForSearch < 0) {
1925
2001
  this.showSearch(false);
@@ -1931,14 +2007,34 @@ the specific language governing permissions and limitations under the Apache Lic
1931
2007
 
1932
2008
  this.focusser = container.find(".select2-focusser");
1933
2009
 
2010
+ // add aria associations
2011
+ selection.find(".select2-chosen").attr("id", "select2-chosen-"+idSuffix);
2012
+ this.focusser.attr("aria-labelledby", "select2-chosen-"+idSuffix);
2013
+ this.results.attr("id", "select2-results-"+idSuffix);
2014
+ this.search.attr("aria-owns", "select2-results-"+idSuffix);
2015
+
1934
2016
  // rewrite labels from original element to focusser
1935
- this.focusser.attr("id", "s2id_autogen"+nextUid());
2017
+ this.focusser.attr("id", "s2id_autogen"+idSuffix);
1936
2018
 
1937
- $("label[for='" + this.opts.element.attr("id") + "']")
2019
+ elementLabel = $("label[for='" + this.opts.element.attr("id") + "']");
2020
+
2021
+ this.focusser.prev()
2022
+ .text(elementLabel.text())
1938
2023
  .attr('for', this.focusser.attr('id'));
1939
2024
 
2025
+ // Ensure the original element retains an accessible name
2026
+ var originalTitle = this.opts.element.attr("title");
2027
+ this.opts.element.attr("title", (originalTitle || elementLabel.text()));
2028
+
1940
2029
  this.focusser.attr("tabindex", this.elementTabIndex);
1941
2030
 
2031
+ // write label for search field using the label from the focusser element
2032
+ this.search.attr("id", this.focusser.attr('id') + '_search');
2033
+
2034
+ this.search.prev()
2035
+ .text($("label[for='" + this.focusser.attr('id') + "']").text())
2036
+ .attr('for', this.search.attr('id'));
2037
+
1942
2038
  this.search.on("keydown", this.bind(function (e) {
1943
2039
  if (!this.isInterfaceEnabled()) return;
1944
2040
 
@@ -1973,7 +2069,9 @@ the specific language governing permissions and limitations under the Apache Lic
1973
2069
  // without this the search field loses focus which is annoying
1974
2070
  if (document.activeElement === this.body().get(0)) {
1975
2071
  window.setTimeout(this.bind(function() {
1976
- this.search.focus();
2072
+ if (this.opened()) {
2073
+ this.search.focus();
2074
+ }
1977
2075
  }), 0);
1978
2076
  }
1979
2077
  }));
@@ -2019,7 +2117,7 @@ the specific language governing permissions and limitations under the Apache Lic
2019
2117
  }
2020
2118
  }));
2021
2119
 
2022
- selection.on("mousedown", "abbr", this.bind(function (e) {
2120
+ selection.on("mousedown touchstart", "abbr", this.bind(function (e) {
2023
2121
  if (!this.isInterfaceEnabled()) return;
2024
2122
  this.clear();
2025
2123
  killEventImmediately(e);
@@ -2027,7 +2125,9 @@ the specific language governing permissions and limitations under the Apache Lic
2027
2125
  this.selection.focus();
2028
2126
  }));
2029
2127
 
2030
- selection.on("mousedown", this.bind(function (e) {
2128
+ selection.on("mousedown touchstart", this.bind(function (e) {
2129
+ // Prevent IE from generating a click event on the body
2130
+ reinsertElement(selection);
2031
2131
 
2032
2132
  if (!this.container.hasClass("select2-container-active")) {
2033
2133
  this.opts.element.trigger($.Event("select2-focus"));
@@ -2042,7 +2142,7 @@ the specific language governing permissions and limitations under the Apache Lic
2042
2142
  killEvent(e);
2043
2143
  }));
2044
2144
 
2045
- dropdown.on("mousedown", this.bind(function() { this.search.focus(); }));
2145
+ dropdown.on("mousedown touchstart", this.bind(function() { this.search.focus(); }));
2046
2146
 
2047
2147
  selection.on("focus", this.bind(function(e) {
2048
2148
  killEvent(e);
@@ -2111,6 +2211,7 @@ the specific language governing permissions and limitations under the Apache Lic
2111
2211
  self.updateSelection(selected);
2112
2212
  self.close();
2113
2213
  self.setPlaceholder();
2214
+ self.nextSearchTerm = self.opts.nextSearchTerm(selected, self.search.val());
2114
2215
  }
2115
2216
  });
2116
2217
  }
@@ -2133,7 +2234,7 @@ the specific language governing permissions and limitations under the Apache Lic
2133
2234
  if (opts.element.get(0).tagName.toLowerCase() === "select") {
2134
2235
  // install the selection initializer
2135
2236
  opts.initSelection = function (element, callback) {
2136
- var selected = element.find("option").filter(function() { return this.selected });
2237
+ var selected = element.find("option").filter(function() { return this.selected && !this.disabled });
2137
2238
  // a single select box always has a value, no need to null check 'selected'
2138
2239
  callback(self.optionToData(selected));
2139
2240
  };
@@ -2250,10 +2351,13 @@ the specific language governing permissions and limitations under the Apache Lic
2250
2351
  this.nextSearchTerm = this.opts.nextSearchTerm(data, this.search.val());
2251
2352
  this.close();
2252
2353
 
2253
- if (!options || !options.noFocus)
2354
+ if ((!options || !options.noFocus) && this.opts.shouldFocusInput(this)) {
2254
2355
  this.focusser.focus();
2356
+ }
2255
2357
 
2256
- if (!equal(old, this.id(data))) { this.triggerChange({added:data,removed:oldData}); }
2358
+ if (!equal(old, this.id(data))) {
2359
+ this.triggerChange({ added: data, removed: oldData });
2360
+ }
2257
2361
  },
2258
2362
 
2259
2363
  // single
@@ -2375,6 +2479,7 @@ the specific language governing permissions and limitations under the Apache Lic
2375
2479
  }).html([
2376
2480
  "<ul class='select2-choices'>",
2377
2481
  " <li class='select2-search-field'>",
2482
+ " <label for='' class='select2-offscreen'></label>",
2378
2483
  " <input type='text' autocomplete='off' autocorrect='off' autocapitalize='off' spellcheck='false' class='select2-input'>",
2379
2484
  " </li>",
2380
2485
  "</ul>",
@@ -2393,12 +2498,12 @@ the specific language governing permissions and limitations under the Apache Lic
2393
2498
  // TODO validate placeholder is a string if specified
2394
2499
 
2395
2500
  if (opts.element.get(0).tagName.toLowerCase() === "select") {
2396
- // install sthe selection initializer
2501
+ // install the selection initializer
2397
2502
  opts.initSelection = function (element, callback) {
2398
2503
 
2399
2504
  var data = [];
2400
2505
 
2401
- element.find("option").filter(function() { return this.selected }).each2(function (i, elm) {
2506
+ element.find("option").filter(function() { return this.selected && !this.disabled }).each2(function (i, elm) {
2402
2507
  data.push(self.optionToData(elm));
2403
2508
  });
2404
2509
  callback(data);
@@ -2486,7 +2591,9 @@ the specific language governing permissions and limitations under the Apache Lic
2486
2591
 
2487
2592
  // rewrite labels from original element to focusser
2488
2593
  this.search.attr("id", "s2id_autogen"+nextUid());
2489
- $("label[for='" + this.opts.element.attr("id") + "']")
2594
+
2595
+ this.search.prev()
2596
+ .text($("label[for='" + this.opts.element.attr("id") + "']").text())
2490
2597
  .attr('for', this.search.attr('id'));
2491
2598
 
2492
2599
  this.search.on("input paste", this.bind(function() {
@@ -2518,13 +2625,15 @@ the specific language governing permissions and limitations under the Apache Lic
2518
2625
  selectedChoice = next.length ? next : null;
2519
2626
  }
2520
2627
  else if (e.which === KEY.BACKSPACE) {
2521
- this.unselect(selected.first());
2522
- this.search.width(10);
2523
- selectedChoice = prev.length ? prev : next;
2628
+ if (this.unselect(selected.first())) {
2629
+ this.search.width(10);
2630
+ selectedChoice = prev.length ? prev : next;
2631
+ }
2524
2632
  } else if (e.which == KEY.DELETE) {
2525
- this.unselect(selected.first());
2526
- this.search.width(10);
2527
- selectedChoice = next.length ? next : null;
2633
+ if (this.unselect(selected.first())) {
2634
+ this.search.width(10);
2635
+ selectedChoice = next.length ? next : null;
2636
+ }
2528
2637
  } else if (e.which == KEY.ENTER) {
2529
2638
  selectedChoice = null;
2530
2639
  }
@@ -2702,6 +2811,15 @@ the specific language governing permissions and limitations under the Apache Lic
2702
2811
 
2703
2812
  this.focusSearch();
2704
2813
 
2814
+ // initializes search's value with nextSearchTerm (if defined by user)
2815
+ // ignore nextSearchTerm if the dropdown is opened by the user pressing a letter
2816
+ if(this.search.val() === "") {
2817
+ if(this.nextSearchTerm != undefined){
2818
+ this.search.val(this.nextSearchTerm);
2819
+ this.search.select();
2820
+ }
2821
+ }
2822
+
2705
2823
  this.updateResults(true);
2706
2824
  this.search.focus();
2707
2825
  this.opts.element.trigger($.Event("select2-open"));
@@ -2766,6 +2884,12 @@ the specific language governing permissions and limitations under the Apache Lic
2766
2884
 
2767
2885
  this.opts.element.trigger({ type: "selected", val: this.id(data), choice: data });
2768
2886
 
2887
+ // keep track of the search's value before it gets cleared
2888
+ this.nextSearchTerm = this.opts.nextSearchTerm(data, this.search.val());
2889
+
2890
+ this.clearSearch();
2891
+ this.updateResults();
2892
+
2769
2893
  if (this.select || !this.opts.closeOnSelect) this.postprocessResults(data, false, this.opts.closeOnSelect===true);
2770
2894
 
2771
2895
  if (this.opts.closeOnSelect) {
@@ -2779,6 +2903,13 @@ the specific language governing permissions and limitations under the Apache Lic
2779
2903
  // if we reached max selection size repaint the results so choices
2780
2904
  // are replaced with the max selection reached message
2781
2905
  this.updateResults(true);
2906
+ } else {
2907
+ // initializes search's value with nextSearchTerm and update search result
2908
+ if(this.nextSearchTerm != undefined){
2909
+ this.search.val(this.nextSearchTerm);
2910
+ this.updateResults();
2911
+ this.search.select();
2912
+ }
2782
2913
  }
2783
2914
  this.positionDropdown();
2784
2915
  } else {
@@ -2807,7 +2938,7 @@ the specific language governing permissions and limitations under the Apache Lic
2807
2938
  enabledItem = $(
2808
2939
  "<li class='select2-search-choice'>" +
2809
2940
  " <div></div>" +
2810
- " <a href='#' onclick='return false;' class='select2-search-choice-close' tabindex='-1'></a>" +
2941
+ " <a href='#' class='select2-search-choice-close' tabindex='-1'></a>" +
2811
2942
  "</li>"),
2812
2943
  disabledItem = $(
2813
2944
  "<li class='select2-search-choice select2-locked'>" +
@@ -2834,13 +2965,11 @@ the specific language governing permissions and limitations under the Apache Lic
2834
2965
  .on("click dblclick", this.bind(function (e) {
2835
2966
  if (!this.isInterfaceEnabled()) return;
2836
2967
 
2837
- $(e.target).closest(".select2-search-choice").fadeOut('fast', this.bind(function(){
2838
- this.unselect($(e.target));
2839
- this.selection.find(".select2-search-choice-focus").removeClass("select2-search-choice-focus");
2840
- this.close();
2841
- this.focusSearch();
2842
- })).dequeue();
2968
+ this.unselect($(e.target));
2969
+ this.selection.find(".select2-search-choice-focus").removeClass("select2-search-choice-focus");
2843
2970
  killEvent(e);
2971
+ this.close();
2972
+ this.focusSearch();
2844
2973
  })).on("focus", this.bind(function () {
2845
2974
  if (!this.isInterfaceEnabled()) return;
2846
2975
  this.container.addClass("select2-container-active");
@@ -2874,25 +3003,27 @@ the specific language governing permissions and limitations under the Apache Lic
2874
3003
  return;
2875
3004
  }
2876
3005
 
2877
- while((index = indexOf(this.id(data), val)) >= 0) {
2878
- val.splice(index, 1);
2879
- this.setVal(val);
2880
- if (this.select) this.postprocessResults();
2881
- }
2882
-
2883
3006
  var evt = $.Event("select2-removing");
2884
3007
  evt.val = this.id(data);
2885
3008
  evt.choice = data;
2886
3009
  this.opts.element.trigger(evt);
2887
3010
 
2888
3011
  if (evt.isDefaultPrevented()) {
2889
- return;
3012
+ return false;
3013
+ }
3014
+
3015
+ while((index = indexOf(this.id(data), val)) >= 0) {
3016
+ val.splice(index, 1);
3017
+ this.setVal(val);
3018
+ if (this.select) this.postprocessResults();
2890
3019
  }
2891
3020
 
2892
3021
  selected.remove();
2893
3022
 
2894
3023
  this.opts.element.trigger({ type: "select2-removed", val: this.id(data), choice: data });
2895
3024
  this.triggerChange({ removed: data });
3025
+
3026
+ return true;
2896
3027
  },
2897
3028
 
2898
3029
  // multi
@@ -2912,7 +3043,7 @@ the specific language governing permissions and limitations under the Apache Lic
2912
3043
  });
2913
3044
 
2914
3045
  compound.each2(function(i, choice) {
2915
- // hide an optgroup if it doesnt have any selectable children
3046
+ // hide an optgroup if it doesn't have any selectable children
2916
3047
  if (!choice.is('.select2-result-selectable')
2917
3048
  && choice.find(".select2-result-selectable:not(.select2-selected)").length === 0) {
2918
3049
  choice.addClass("select2-selected");
@@ -2923,11 +3054,11 @@ the specific language governing permissions and limitations under the Apache Lic
2923
3054
  self.highlight(0);
2924
3055
  }
2925
3056
 
2926
- //If all results are chosen render formatNoMAtches
3057
+ //If all results are chosen render formatNoMatches
2927
3058
  if(!this.opts.createSearchChoice && !choices.filter('.select2-result:not(.select2-selected)').length > 0){
2928
3059
  if(!data || data && !data.more && this.results.find(".select2-no-results").length === 0) {
2929
3060
  if (checkFormatter(self.opts.formatNoMatches, "formatNoMatches")) {
2930
- this.results.append("<li class='select2-no-results'>" + self.opts.formatNoMatches(self.search.val()) + "</li>");
3061
+ this.results.append("<li class='select2-no-results'>" + evaluate(self.opts.formatNoMatches, self.search.val()) + "</li>");
2931
3062
  }
2932
3063
  }
2933
3064
  }
@@ -3103,7 +3234,7 @@ the specific language governing permissions and limitations under the Apache Lic
3103
3234
  var self=this, ids, old;
3104
3235
  if (arguments.length === 0) {
3105
3236
  return this.selection
3106
- .find(".select2-search-choice")
3237
+ .children(".select2-search-choice")
3107
3238
  .map(function() { return $(this).data("select2-data"); })
3108
3239
  .get();
3109
3240
  } else {
@@ -3143,7 +3274,7 @@ the specific language governing permissions and limitations under the Apache Lic
3143
3274
  if ("tags" in opts) {opts.multiple = multiple = true;}
3144
3275
  }
3145
3276
 
3146
- select2 = multiple ? new MultiSelect2() : new SingleSelect2();
3277
+ select2 = multiple ? new window.Select2["class"].multi() : new window.Select2["class"].single();
3147
3278
  select2.init(opts);
3148
3279
  } else if (typeof(args[0]) === "string") {
3149
3280
 
@@ -3198,19 +3329,20 @@ the specific language governing permissions and limitations under the Apache Lic
3198
3329
  sortResults: function (results, container, query) {
3199
3330
  return results;
3200
3331
  },
3201
- formatResultCssClass: function(data) {return undefined;},
3332
+ formatResultCssClass: function(data) {return data.css;},
3202
3333
  formatSelectionCssClass: function(data, container) {return undefined;},
3334
+ formatMatches: function (matches) { return matches + " results are available, use up and down arrow keys to navigate."; },
3203
3335
  formatNoMatches: function () { return "No matches found"; },
3204
- formatInputTooShort: function (input, min) { var n = min - input.length; return "Please enter " + n + " more character" + (n == 1? "" : "s"); },
3336
+ formatInputTooShort: function (input, min) { var n = min - input.length; return "Please enter " + n + " or more character" + (n == 1? "" : "s"); },
3205
3337
  formatInputTooLong: function (input, max) { var n = input.length - max; return "Please delete " + n + " character" + (n == 1? "" : "s"); },
3206
3338
  formatSelectionTooBig: function (limit) { return "You can only select " + limit + " item" + (limit == 1 ? "" : "s"); },
3207
- formatLoadMore: function (pageNumber) { return "Loading more results..."; },
3208
- formatSearching: function () { return "Searching..."; },
3339
+ formatLoadMore: function (pageNumber) { return "Loading more results"; },
3340
+ formatSearching: function () { return "Searching"; },
3209
3341
  minimumResultsForSearch: 0,
3210
3342
  minimumInputLength: 0,
3211
3343
  maximumInputLength: null,
3212
3344
  maximumSelectionSize: 0,
3213
- id: function (e) { return e.id; },
3345
+ id: function (e) { return e == undefined ? null : e.id; },
3214
3346
  matcher: function(term, text) {
3215
3347
  return stripDiacritics(''+text).toUpperCase().indexOf(stripDiacritics(''+term).toUpperCase()) >= 0;
3216
3348
  },
@@ -3222,7 +3354,17 @@ the specific language governing permissions and limitations under the Apache Lic
3222
3354
  selectOnBlur: false,
3223
3355
  adaptContainerCssClass: function(c) { return c; },
3224
3356
  adaptDropdownCssClass: function(c) { return null; },
3225
- nextSearchTerm: function(selectedObject, currentSearchTerm) { return undefined; }
3357
+ nextSearchTerm: function(selectedObject, currentSearchTerm) { return undefined; },
3358
+ searchInputPlaceholder: '',
3359
+ createSearchChoicePosition: 'top',
3360
+ shouldFocusInput: function (instance) {
3361
+ // Never focus the input if search is disabled
3362
+ if (instance.opts.minimumResultsForSearch < 0) {
3363
+ return false;
3364
+ }
3365
+
3366
+ return true;
3367
+ }
3226
3368
  };
3227
3369
 
3228
3370
  $.fn.select2.ajaxDefaults = {