autocomplete-rails.js 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. /*
  2. * Unobtrusive autocomplete
  3. *
  4. * To use it, you just have to include the HTML attribute autocomplete
  5. * with the autocomplete URL as the value
  6. *
  7. * Example:
  8. * <input type="text" data-autocomplete="/url/to/autocomplete">
  9. *
  10. * Optionally, you can use a jQuery selector to specify a field that can
  11. * be updated with the element id whenever you find a matching value
  12. *
  13. * Example:
  14. * <input type="text" data-autocomplete="/url/to/autocomplete" data-id-element="#id_field">
  15. */
  16. (function(jQuery)
  17. {
  18. var self = null;
  19. jQuery.fn.railsAutocomplete = function() {
  20. return this.live('focus',function() {
  21. if (!this.railsAutoCompleter) {
  22. this.railsAutoCompleter = new jQuery.railsAutocomplete(this);
  23. }
  24. });
  25. };
  26. jQuery.railsAutocomplete = function (e) {
  27. _e = e;
  28. this.init(_e);
  29. };
  30. jQuery.railsAutocomplete.fn = jQuery.railsAutocomplete.prototype = {
  31. railsAutocomplete: '0.0.1'
  32. };
  33. jQuery.railsAutocomplete.fn.extend = jQuery.railsAutocomplete.extend = jQuery.extend;
  34. jQuery.railsAutocomplete.fn.extend({
  35. init: function(e) {
  36. e.delimiter = jQuery(e).attr('data-delimiter') || null;
  37. function split( val ) {
  38. return val.split( e.delimiter );
  39. }
  40. function extractLast( term ) {
  41. return split( term ).pop().replace(/^\s+/,"");
  42. }
  43. jQuery(e).autocomplete({
  44. source: function( request, response ) {
  45. jQuery.getJSON( jQuery(e).attr('data-autocomplete'), {
  46. term: extractLast( request.term )
  47. }, function() {
  48. jQuery(arguments[0]).each(function(i, el) {
  49. var obj = {};
  50. obj[el.id] = el;
  51. jQuery(e).data(obj);
  52. });
  53. response.apply(null, arguments);
  54. });
  55. },
  56. search: function() {
  57. // custom minLength
  58. var term = extractLast( this.value );
  59. if ( term.length < 2 ) {
  60. return false;
  61. }
  62. },
  63. focus: function() {
  64. // prevent value inserted on focus
  65. return false;
  66. },
  67. select: function( event, ui ) {
  68. var terms = split( this.value );
  69. // remove the current input
  70. terms.pop();
  71. // add the selected item
  72. terms.push( ui.item.value );
  73. // add placeholder to get the comma-and-space at the end
  74. if (e.delimiter != null) {
  75. terms.push( "" );
  76. this.value = terms.join( e.delimiter );
  77. } else {
  78. this.value = terms.join("");
  79. if (jQuery(this).attr('data-id-element')) {
  80. jQuery(jQuery(this).attr('data-id-element')).val(ui.item.id);
  81. }
  82. if (jQuery(this).attr('data-update-elements')) {
  83. var data = jQuery(this).data(ui.item.id.toString());
  84. var update_elements = jQuery.parseJSON(jQuery(this).attr("data-update-elements"));
  85. for (var key in update_elements) {
  86. jQuery(update_elements[key]).val(data[key]);
  87. }
  88. }
  89. }
  90. var remember_string = this.value;
  91. jQuery(this).bind('keyup.clearId', function(){
  92. if(jQuery(this).val().trim() != remember_string.trim()){
  93. jQuery(jQuery(this).attr('data-id-element')).val("");
  94. jQuery(this).unbind('keyup.clearId');
  95. }
  96. });
  97. jQuery(this).trigger('railsAutocomplete.select', ui);
  98. return false;
  99. }
  100. });
  101. }
  102. });
  103. jQuery(document).ready(function(){
  104. jQuery('input[data-autocomplete]').railsAutocomplete();
  105. });
  106. })(jQuery);