rails_tokeninput 1.6.1.rc1 → 1.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,2 @@
1
+ /*! jquery.tokeninput 2014-04-02 */
2
+ !function(a){function b(a){return String(null===a||void 0===a?"":a)}function c(a){return b(a).replace(i,function(a){return h[a]})}var d={method:"GET",queryParam:"q",searchDelay:300,minChars:1,propertyToSearch:"name",jsonContainer:null,contentType:"json",excludeCurrent:!1,excludeCurrentParameter:"x",prePopulate:null,processPrePopulate:!1,hintText:"Type in a search term",noResultsText:"No results",searchingText:"Searching...",deleteText:"&#215;",animateDropdown:!0,placeholder:null,theme:null,zindex:999,resultsLimit:null,enableHTML:!1,resultsFormatter:function(a){var b=a[this.propertyToSearch];return"<li>"+(this.enableHTML?b:c(b))+"</li>"},tokenFormatter:function(a){var b=a[this.propertyToSearch];return"<li><p>"+(this.enableHTML?b:c(b))+"</p></li>"},tokenLimit:null,tokenDelimiter:",",preventDuplicates:!1,tokenValue:"id",allowFreeTagging:!1,allowTabOut:!1,autoSelectFirstResult:!1,onResult:null,onCachedResult:null,onAdd:null,onFreeTaggingAdd:null,onDelete:null,onReady:null,idPrefix:"token-input-",disabled:!1},e={tokenList:"token-input-list",token:"token-input-token",tokenReadOnly:"token-input-token-readonly",tokenDelete:"token-input-delete-token",selectedToken:"token-input-selected-token",highlightedToken:"token-input-highlighted-token",dropdown:"token-input-dropdown",dropdownItem:"token-input-dropdown-item",dropdownItem2:"token-input-dropdown-item2",selectedDropdownItem:"token-input-selected-dropdown-item",inputToken:"token-input-input-token",focused:"token-input-focused",disabled:"token-input-disabled"},f={BEFORE:0,AFTER:1,END:2},g={BACKSPACE:8,TAB:9,ENTER:13,ESCAPE:27,SPACE:32,PAGE_UP:33,PAGE_DOWN:34,END:35,HOME:36,LEFT:37,UP:38,RIGHT:39,DOWN:40,NUMPAD_ENTER:108,COMMA:188},h={"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#x27;","/":"&#x2F;"},i=/[&<>"'\/]/g,j={init:function(b,c){var e=a.extend({},d,c||{});return this.each(function(){a(this).data("settings",e),a(this).data("tokenInputObject",new a.TokenList(this,b,e))})},clear:function(){return this.data("tokenInputObject").clear(),this},add:function(a){return this.data("tokenInputObject").add(a),this},remove:function(a){return this.data("tokenInputObject").remove(a),this},get:function(){return this.data("tokenInputObject").getTokens()},toggleDisabled:function(a){return this.data("tokenInputObject").toggleDisabled(a),this},setOptions:function(b){return a(this).data("settings",a.extend({},a(this).data("settings"),b||{})),this},destroy:function(){if(this.data("tokenInputObject")){this.data("tokenInputObject").clear();var a=this,b=this.parent();return b.empty(),a.show(),b.append(a),a}}};a.fn.tokenInput=function(a){return j[a]?j[a].apply(this,Array.prototype.slice.call(arguments,1)):j.init.apply(this,arguments)},a.TokenList=function(b,d,h){function i(d){return a(b).data("settings").enableHTML?d:c(d)}function j(c){a(b).data("settings").disabled="boolean"==typeof c?c:!a(b).data("settings").disabled,P.attr("disabled",a(b).data("settings").disabled),U.toggleClass(a(b).data("settings").classes.disabled,a(b).data("settings").disabled),R&&q(a(R),f.END),Q.attr("disabled",a(b).data("settings").disabled)}function k(){return null!==a(b).data("settings").tokenLimit&&N>=a(b).data("settings").tokenLimit?(P.hide(),void u()):void 0}function l(){if(L!==(L=P.val())){var a=U.width()-P.offset().left-U.offset().left;X.html(c(L)||c(h.placeholder)),P.width(Math.min(U.width(),Math.max(a,X.width()+30)))}}function m(){var c=a.trim(P.val()),d=c.split(a(b).data("settings").tokenDelimiter);a.each(d,function(c,d){if(d){a.isFunction(a(b).data("settings").onFreeTaggingAdd)&&(d=a(b).data("settings").onFreeTaggingAdd.call(Q,d));var e={};e[a(b).data("settings").tokenValue]=e[a(b).data("settings").propertyToSearch]=d,o(e)}})}function n(c){var d=a(a(b).data("settings").tokenFormatter(c)),e=c.readonly===!0?!0:!1;e&&d.addClass(a(b).data("settings").classes.tokenReadOnly),d.addClass(a(b).data("settings").classes.token).insertBefore(V),e||a("<span>"+a(b).data("settings").deleteText+"</span>").addClass(a(b).data("settings").classes.tokenDelete).appendTo(d).click(function(){return a(b).data("settings").disabled?void 0:(s(a(this).parent()),Q.change(),!1)});var f=c;return a.data(d.get(0),"tokeninput",c),M=M.slice(0,S).concat([f]).concat(M.slice(S)),S++,t(M,Q),N+=1,null!==a(b).data("settings").tokenLimit&&N>=a(b).data("settings").tokenLimit&&(P.hide(),u()),d}function o(c){var d=a(b).data("settings").onAdd;if(N>0&&a(b).data("settings").preventDuplicates){var e=null;if(U.children().each(function(){var b=a(this),d=a.data(b.get(0),"tokeninput");return d&&d[h.tokenValue]===c[h.tokenValue]?(e=b,!1):void 0}),e)return p(e),V.insertAfter(e),void I(P)}P.width(1),(null==a(b).data("settings").tokenLimit||N<a(b).data("settings").tokenLimit)&&(n(c),P.attr("placeholder",null),k()),P.val(""),u(),a.isFunction(d)&&d.call(Q,c)}function p(c){a(b).data("settings").disabled||(c.addClass(a(b).data("settings").classes.selectedToken),R=c.get(0),P.val(""),u())}function q(c,d){c.removeClass(a(b).data("settings").classes.selectedToken),R=null,d===f.BEFORE?(V.insertBefore(c),S--):d===f.AFTER?(V.insertAfter(c),S++):(V.appendTo(U),S=N),I(P)}function r(b){var c=R;R&&q(a(R),f.END),c===b.get(0)?q(b,f.END):p(b)}function s(c){var d=a.data(c.get(0),"tokeninput"),e=a(b).data("settings").onDelete,f=c.prevAll().length;f>S&&f--,c.remove(),R=null,I(P),M=M.slice(0,f).concat(M.slice(f+1)),0==M.length&&P.attr("placeholder",h.placeholder),S>f&&S--,t(M,Q),N-=1,null!==a(b).data("settings").tokenLimit&&(P.show().val(""),I(P)),a.isFunction(e)&&e.call(Q,d)}function t(c,d){var e=a.map(c,function(c){return"function"==typeof a(b).data("settings").tokenValue?a(b).data("settings").tokenValue.call(this,c):c[a(b).data("settings").tokenValue]});d.val(e.join(a(b).data("settings").tokenDelimiter))}function u(){W.hide().empty(),T=null}function v(){W.css({position:"absolute",top:U.offset().top+U.outerHeight(!0),left:U.offset().left,width:U.width(),"z-index":a(b).data("settings").zindex}).show()}function w(){a(b).data("settings").searchingText&&(W.html("<p>"+i(a(b).data("settings").searchingText)+"</p>"),v())}function x(){a(b).data("settings").hintText&&(W.html("<p>"+i(a(b).data("settings").hintText)+"</p>"),v())}function y(a){return a.replace(Z,"\\$&")}function z(a,b){return a.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)("+y(b)+")(?![^<>]*>)(?![^&;]+;)","gi"),function(a,b){return"<b>"+i(b)+"</b>"})}function A(a,b,c){return a.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)("+y(b)+")(?![^<>]*>)(?![^&;]+;)","g"),z(b,c))}function B(c){if(a(b).data("settings").excludeCurrent){var d=a(b).data("tokenInputObject").getTokens(),e=[];d.length&&(a.each(c,function(c,f){var g=!0;a.each(d,function(c,d){return f[a(b).data("settings").propertyToSearch]==d[a(b).data("settings").propertyToSearch]?(g=!1,!1):void 0}),g&&e.push(f)}),c=e)}return c}function C(c,d){if(d=B(d),d&&d.length){W.empty();var e=a("<ul/>").appendTo(W).mouseover(function(b){D(a(b.target).closest("li"))}).mousedown(function(b){return o(a(b.target).closest("li").data("tokeninput")),Q.change(),!1}).hide();a(b).data("settings").resultsLimit&&d.length>a(b).data("settings").resultsLimit&&(d=d.slice(0,a(b).data("settings").resultsLimit)),a.each(d,function(d,f){var g=a(b).data("settings").resultsFormatter(f);g=A(g,f[a(b).data("settings").propertyToSearch],c),g=a(g).appendTo(e),g.addClass(d%2?a(b).data("settings").classes.dropdownItem:a(b).data("settings").classes.dropdownItem2),0===d&&a(b).data("settings").autoSelectFirstResult&&D(g),a.data(g.get(0),"tokeninput",f)}),v(),a(b).data("settings").animateDropdown?e.slideDown("fast"):e.show()}else a(b).data("settings").noResultsText&&(W.html("<p>"+i(a(b).data("settings").noResultsText)+"</p>"),v())}function D(c){c&&(T&&E(a(T)),c.addClass(a(b).data("settings").classes.selectedDropdownItem),T=c.get(0))}function E(c){c.removeClass(a(b).data("settings").classes.selectedDropdownItem),T=null}function F(){var c=P.val();c&&c.length&&(R&&q(a(R),f.AFTER),c.length>=a(b).data("settings").minChars?(w(),clearTimeout(K),K=setTimeout(function(){G(c)},a(b).data("settings").searchDelay)):u())}function G(c){var d=c+H(),e=O.get(d);if(e)a.isFunction(a(b).data("settings").onCachedResult)&&(e=a(b).data("settings").onCachedResult.call(Q,e)),C(c,e);else if(a(b).data("settings").url){var f=H(),g={};if(g.data={},f.indexOf("?")>-1){var i=f.split("?");g.url=i[0];var j=i[1].split("&");a.each(j,function(a,b){var c=b.split("=");g.data[c[0]]=c[1]})}else g.url=f;if(g.data[a(b).data("settings").queryParam]=c,g.type=a(b).data("settings").method,g.dataType=a(b).data("settings").contentType,a(b).data("settings").crossDomain&&(g.dataType="jsonp"),a(b).data("settings").excludeCurrent){var k=a(b).data("tokenInputObject").getTokens(),l=a.map(k,function(c){return"function"==typeof a(b).data("settings").tokenValue?a(b).data("settings").tokenValue.call(this,c):c[a(b).data("settings").tokenValue]});g.data[a(b).data("settings").excludeCurrentParameter]=l.join(a(b).data("settings").tokenDelimiter)}g.success=function(e){O.add(d,a(b).data("settings").jsonContainer?e[a(b).data("settings").jsonContainer]:e),a.isFunction(a(b).data("settings").onResult)&&(e=a(b).data("settings").onResult.call(Q,e)),P.val()===c&&C(c,a(b).data("settings").jsonContainer?e[a(b).data("settings").jsonContainer]:e)},h.onSend&&h.onSend(g),a.ajax(g)}else if(a(b).data("settings").local_data){var m=a.grep(a(b).data("settings").local_data,function(d){return d[a(b).data("settings").propertyToSearch].toLowerCase().indexOf(c.toLowerCase())>-1});O.add(d,m),a.isFunction(a(b).data("settings").onResult)&&(m=a(b).data("settings").onResult.call(Q,m)),C(c,m)}}function H(){var c=a(b).data("settings").url;return"function"==typeof a(b).data("settings").url&&(c=a(b).data("settings").url.call(a(b).data("settings"))),c}function I(a){setTimeout(function(){a.focus()},50)}if("string"==typeof d||"function"==typeof d){a(b).data("settings").url=d;var J=H();void 0===a(b).data("settings").crossDomain&&"string"==typeof J&&(a(b).data("settings").crossDomain=-1===J.indexOf("://")?!1:location.href.split(/\/+/g)[1]!==J.split(/\/+/g)[1])}else"object"==typeof d&&(a(b).data("settings").local_data=d);a(b).data("settings").classes?a(b).data("settings").classes=a.extend({},e,a(b).data("settings").classes):a(b).data("settings").theme?(a(b).data("settings").classes={},a.each(e,function(c,d){a(b).data("settings").classes[c]=d+"-"+a(b).data("settings").theme})):a(b).data("settings").classes=e;var K,L,M=[],N=0,O=new a.TokenList.Cache,P=a('<input type="text" autocomplete="off" autocapitalize="off"/>').css({outline:"none"}).attr("id",a(b).data("settings").idPrefix+b.id).focus(function(){return a(b).data("settings").disabled?!1:((null===a(b).data("settings").tokenLimit||a(b).data("settings").tokenLimit!==N)&&x(),void U.addClass(a(b).data("settings").classes.focused))}).blur(function(){u(),a(b).data("settings").allowFreeTagging&&m(),a(this).val(""),U.removeClass(a(b).data("settings").classes.focused)}).bind("keyup keydown blur update",l).keydown(function(c){var d,e;switch(c.keyCode){case g.LEFT:case g.RIGHT:case g.UP:case g.DOWN:if(0===this.value.length)d=V.prev(),e=V.next(),d.length&&d.get(0)===R||e.length&&e.get(0)===R?c.keyCode===g.LEFT||c.keyCode===g.UP?q(a(R),f.BEFORE):q(a(R),f.AFTER):c.keyCode!==g.LEFT&&c.keyCode!==g.UP||!d.length?c.keyCode!==g.RIGHT&&c.keyCode!==g.DOWN||!e.length||p(a(e.get(0))):p(a(d.get(0)));else{var h=null;c.keyCode===g.DOWN||c.keyCode===g.RIGHT?(h=a(W).find("li").first(),T&&(h=a(T).next())):(h=a(W).find("li").last(),T&&(h=a(T).prev())),D(h)}break;case g.BACKSPACE:if(d=V.prev(),0===this.value.length)return R?(s(a(R)),Q.change()):d.length&&p(a(d.get(0))),!1;1===a(this).val().length?u():setTimeout(function(){F()},5);break;case g.TAB:case g.ENTER:case g.NUMPAD_ENTER:case g.COMMA:if(T)o(a(T).data("tokeninput")),Q.change();else{if(a(b).data("settings").allowFreeTagging){if(a(b).data("settings").allowTabOut&&""===a(this).val())return!0;m()}else if(a(this).val(""),a(b).data("settings").allowTabOut)return!0;c.stopPropagation(),c.preventDefault()}return!1;case g.ESCAPE:return u(),!0;default:String.fromCharCode(c.which)&&setTimeout(function(){F()},5)}});h.placeholder&&P.attr("placeholder",h.placeholder);var Q=a(b).hide().val("").focus(function(){I(P)}).blur(function(){return P.blur(),Q}),R=null,S=0,T=null,U=a("<ul />").addClass(a(b).data("settings").classes.tokenList).click(function(b){var c=a(b.target).closest("li");c&&c.get(0)&&a.data(c.get(0),"tokeninput")?r(c):(R&&q(a(R),f.END),I(P))}).mouseover(function(c){var d=a(c.target).closest("li");d&&R!==this&&d.addClass(a(b).data("settings").classes.highlightedToken)}).mouseout(function(c){var d=a(c.target).closest("li");d&&R!==this&&d.removeClass(a(b).data("settings").classes.highlightedToken)}).insertBefore(Q),V=a("<li />").addClass(a(b).data("settings").classes.inputToken).appendTo(U).append(P),W=a("<div/>").addClass(a(b).data("settings").classes.dropdown).appendTo("body").hide(),X=a("<tester/>").insertAfter(P).css({position:"absolute",top:-9999,left:-9999,width:"auto",fontSize:P.css("fontSize"),fontFamily:P.css("fontFamily"),fontWeight:P.css("fontWeight"),letterSpacing:P.css("letterSpacing"),whiteSpace:"nowrap"});Q.val("");var Y=a(b).data("settings").prePopulate||Q.data("pre");a(b).data("settings").processPrePopulate&&a.isFunction(a(b).data("settings").onResult)&&(Y=a(b).data("settings").onResult.call(Q,Y)),Y&&Y.length&&a.each(Y,function(a,b){n(b),k(),P.attr("placeholder",null)}),a(b).data("settings").disabled&&j(!0),"function"==typeof a(b).data("settings").onReady&&a(b).data("settings").onReady.call(),this.clear=function(){U.children("li").each(function(){0===a(this).children("input").length&&s(a(this))})},this.add=function(a){o(a)},this.remove=function(b){U.children("li").each(function(){if(0===a(this).children("input").length){var c=a(this).data("tokeninput"),d=!0;for(var e in b)if(b[e]!==c[e]){d=!1;break}d&&s(a(this))}})},this.getTokens=function(){return M},this.toggleDisabled=function(a){j(a)},l();var Z=new RegExp("[.\\\\+*?\\[\\^\\]$(){}=!<>|:\\-]","g")},a.TokenList.Cache=function(b){var c,d,e={},f=0;c=a.extend({max_size:500},b),d=function(){e={},f=0},this.add=function(a,b){f>c.max_size&&d(),e[a]||(f+=1),e[a]=b},this.get=function(a){return e[a]}}}(jQuery);
@@ -7,7 +7,7 @@ ul.token-input-list {
7
7
  border: 1px solid #999;
8
8
  cursor: text;
9
9
  font-size: 12px;
10
- font-family: Verdana;
10
+ font-family: Verdana, sans-serif;
11
11
  z-index: 999;
12
12
  margin: 0;
13
13
  padding: 0;
@@ -28,6 +28,21 @@ ul.token-input-list li input {
28
28
  -webkit-appearance: caret;
29
29
  }
30
30
 
31
+ ul.token-input-disabled,
32
+ ul.token-input-disabled li input {
33
+ background-color: #E8E8E8;
34
+ }
35
+
36
+ ul.token-input-disabled li.token-input-token {
37
+ background-color: #D9E3CA;
38
+ color: #7D7D7D
39
+ }
40
+
41
+ ul.token-input-disabled li.token-input-token span {
42
+ color: #CFCFCF;
43
+ cursor: default;
44
+ }
45
+
31
46
  li.token-input-token {
32
47
  overflow: hidden;
33
48
  height: auto !important;
@@ -72,7 +87,7 @@ div.token-input-dropdown {
72
87
  border-bottom: 1px solid #ccc;
73
88
  cursor: default;
74
89
  font-size: 12px;
75
- font-family: Verdana;
90
+ font-family: Verdana, sans-serif;
76
91
  z-index: 1;
77
92
  }
78
93
 
@@ -110,4 +125,3 @@ div.token-input-dropdown ul li em {
110
125
  div.token-input-dropdown ul li.token-input-selected-dropdown-item {
111
126
  background-color: #d0efa0;
112
127
  }
113
-
@@ -1,3 +1,3 @@
1
1
  module RailsTokeninput
2
- VERSION = "1.6.1.rc1"
2
+ VERSION = "1.7.0"
3
3
  end
@@ -12,11 +12,11 @@ Gem::Specification.new do |s|
12
12
  s.description = %q{Gem installation of jquery tokeninput scripts and stylesheets}
13
13
 
14
14
  s.rubyforge_project = "rails_tokeninput"
15
-
15
+
16
16
  s.files = `git ls-files`.split("\n")
17
17
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
18
  s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
- s.require_paths = ["lib", "vendor"]
19
+ s.require_paths = ["lib", "app"]
20
20
 
21
21
  s.add_dependency "railties", ">= 3.1.0"
22
22
  s.add_development_dependency "bundler", "~> 1.0.0"
metadata CHANGED
@@ -1,49 +1,57 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rails_tokeninput
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.6.1.rc1
5
- prerelease: 6
4
+ version: 1.7.0
6
5
  platform: ruby
7
6
  authors:
8
7
  - Han
9
8
  autorequire:
10
9
  bindir: bin
11
10
  cert_chain: []
12
- date: 2012-07-04 00:00:00.000000000Z
11
+ date: 2015-02-15 00:00:00.000000000 Z
13
12
  dependencies:
14
13
  - !ruby/object:Gem::Dependency
15
14
  name: railties
16
- requirement: &70250781782560 !ruby/object:Gem::Requirement
17
- none: false
15
+ requirement: !ruby/object:Gem::Requirement
18
16
  requirements:
19
- - - ! '>='
17
+ - - ">="
20
18
  - !ruby/object:Gem::Version
21
19
  version: 3.1.0
22
20
  type: :runtime
23
21
  prerelease: false
24
- version_requirements: *70250781782560
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: 3.1.0
25
27
  - !ruby/object:Gem::Dependency
26
28
  name: bundler
27
- requirement: &70250781782060 !ruby/object:Gem::Requirement
28
- none: false
29
+ requirement: !ruby/object:Gem::Requirement
29
30
  requirements:
30
- - - ~>
31
+ - - "~>"
31
32
  - !ruby/object:Gem::Version
32
33
  version: 1.0.0
33
34
  type: :development
34
35
  prerelease: false
35
- version_requirements: *70250781782060
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: 1.0.0
36
41
  - !ruby/object:Gem::Dependency
37
42
  name: rails
38
- requirement: &70250781781500 !ruby/object:Gem::Requirement
39
- none: false
43
+ requirement: !ruby/object:Gem::Requirement
40
44
  requirements:
41
- - - ~>
45
+ - - "~>"
42
46
  - !ruby/object:Gem::Version
43
47
  version: '3.1'
44
48
  type: :development
45
49
  prerelease: false
46
- version_requirements: *70250781781500
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '3.1'
47
55
  description: Gem installation of jquery tokeninput scripts and stylesheets
48
56
  email:
49
57
  - han@logicallsat.com
@@ -51,46 +59,42 @@ executables: []
51
59
  extensions: []
52
60
  extra_rdoc_files: []
53
61
  files:
54
- - .DS_Store
55
- - .gitignore
62
+ - ".gitignore"
56
63
  - Gemfile
64
+ - MIT_LICENSE
57
65
  - README.md
58
66
  - Rakefile
59
- - lib/.DS_Store
67
+ - app/assets/javascripts/jquery.tokeninput.js
68
+ - app/assets/javascripts/jquery.tokeninput.min.js
69
+ - app/assets/stylesheets/token-input-facebook.css
70
+ - app/assets/stylesheets/token-input-mac.css
71
+ - app/assets/stylesheets/token-input.css
60
72
  - lib/rails_tokeninput.rb
61
73
  - lib/rails_tokeninput/engine.rb
62
74
  - lib/rails_tokeninput/version.rb
63
75
  - rails_tokeninput.gemspec
64
- - vendor/.DS_Store
65
- - vendor/assets/.DS_Store
66
- - vendor/assets/javascripts/jquery.tokeninput.js
67
- - vendor/assets/stylesheets/token-input-facebook.css
68
- - vendor/assets/stylesheets/token-input-mac.css
69
- - vendor/assets/stylesheets/token-input.css
70
76
  homepage: ''
71
77
  licenses: []
78
+ metadata: {}
72
79
  post_install_message:
73
80
  rdoc_options: []
74
81
  require_paths:
75
82
  - lib
76
- - vendor
83
+ - app
77
84
  required_ruby_version: !ruby/object:Gem::Requirement
78
- none: false
79
85
  requirements:
80
- - - ! '>='
86
+ - - ">="
81
87
  - !ruby/object:Gem::Version
82
88
  version: '0'
83
89
  required_rubygems_version: !ruby/object:Gem::Requirement
84
- none: false
85
90
  requirements:
86
- - - ! '>'
91
+ - - ">="
87
92
  - !ruby/object:Gem::Version
88
- version: 1.3.1
93
+ version: '0'
89
94
  requirements: []
90
95
  rubyforge_project: rails_tokeninput
91
- rubygems_version: 1.8.6
96
+ rubygems_version: 2.2.2
92
97
  signing_key:
93
- specification_version: 3
98
+ specification_version: 4
94
99
  summary: Jquery Tokeninput automated install for Rails 3.1+
95
100
  test_files: []
96
- has_rdoc:
data/.DS_Store DELETED
Binary file
Binary file
Binary file
Binary file
@@ -1,930 +0,0 @@
1
- /*
2
- * jQuery Plugin: Tokenizing Autocomplete Text Entry
3
- * Version 1.6.0
4
- *
5
- * Copyright (c) 2009 James Smith (http://loopj.com)
6
- * Licensed jointly under the GPL and MIT licenses,
7
- * choose which one suits your project best!
8
- *
9
- */
10
-
11
- (function ($) {
12
- // Default settings
13
- var DEFAULT_SETTINGS = {
14
- // Search settings
15
- method: "GET",
16
- queryParam: "q",
17
- searchDelay: 300,
18
- minChars: 1,
19
- propertyToSearch: "name",
20
- jsonContainer: null,
21
- contentType: "json",
22
-
23
- // Prepopulation settings
24
- prePopulate: null,
25
- processPrePopulate: false,
26
-
27
- // Display settings
28
- hintText: "Type in a search term",
29
- noResultsText: "No results",
30
- searchingText: "Searching...",
31
- deleteText: "&times;",
32
- animateDropdown: true,
33
- theme: null,
34
- zindex: 999,
35
- resultsLimit: null,
36
- resultsFormatter: function(item){ return "<li>" + item[this.propertyToSearch]+ "</li>" },
37
- tokenFormatter: function(item) { return "<li><p>" + item[this.propertyToSearch] + "</p></li>" },
38
-
39
- // Tokenization settings
40
- tokenLimit: null,
41
- tokenDelimiter: ",",
42
- preventDuplicates: false,
43
- tokenValue: "id",
44
-
45
- // Callbacks
46
- onResult: null,
47
- onAdd: null,
48
- onDelete: null,
49
- onReady: null,
50
-
51
- // Other settings
52
- idPrefix: "token-input-",
53
-
54
- // Keep track if the input is currently in disabled mode
55
- disabled: false
56
- };
57
-
58
- // Default classes to use when theming
59
- var DEFAULT_CLASSES = {
60
- tokenList: "token-input-list",
61
- token: "token-input-token",
62
- tokenReadOnly: "token-input-token-readonly",
63
- tokenDelete: "token-input-delete-token",
64
- selectedToken: "token-input-selected-token",
65
- highlightedToken: "token-input-highlighted-token",
66
- dropdown: "token-input-dropdown",
67
- dropdownItem: "token-input-dropdown-item",
68
- dropdownItem2: "token-input-dropdown-item2",
69
- selectedDropdownItem: "token-input-selected-dropdown-item",
70
- inputToken: "token-input-input-token",
71
- focused: "token-input-focused",
72
- disabled: "token-input-disabled"
73
- };
74
-
75
- // Input box position "enum"
76
- var POSITION = {
77
- BEFORE: 0,
78
- AFTER: 1,
79
- END: 2
80
- };
81
-
82
- // Keys "enum"
83
- var KEY = {
84
- BACKSPACE: 8,
85
- TAB: 9,
86
- ENTER: 13,
87
- ESCAPE: 27,
88
- SPACE: 32,
89
- PAGE_UP: 33,
90
- PAGE_DOWN: 34,
91
- END: 35,
92
- HOME: 36,
93
- LEFT: 37,
94
- UP: 38,
95
- RIGHT: 39,
96
- DOWN: 40,
97
- NUMPAD_ENTER: 108,
98
- COMMA: 188
99
- };
100
-
101
- // Additional public (exposed) methods
102
- var methods = {
103
- init: function(url_or_data_or_function, options) {
104
- var settings = $.extend({}, DEFAULT_SETTINGS, options || {});
105
-
106
- return this.each(function () {
107
- $(this).data("tokenInputObject", new $.TokenList(this, url_or_data_or_function, settings));
108
- });
109
- },
110
- clear: function() {
111
- this.data("tokenInputObject").clear();
112
- return this;
113
- },
114
- add: function(item) {
115
- this.data("tokenInputObject").add(item);
116
- return this;
117
- },
118
- remove: function(item) {
119
- this.data("tokenInputObject").remove(item);
120
- return this;
121
- },
122
- get: function() {
123
- return this.data("tokenInputObject").getTokens();
124
- },
125
- toggleDisabled: function(disable) {
126
- this.data("tokenInputObject").toggleDisabled(disable);
127
- return this;
128
- }
129
- }
130
-
131
- // Expose the .tokenInput function to jQuery as a plugin
132
- $.fn.tokenInput = function (method) {
133
- // Method calling and initialization logic
134
- if(methods[method]) {
135
- return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));
136
- } else {
137
- return methods.init.apply(this, arguments);
138
- }
139
- };
140
-
141
- // TokenList class for each input
142
- $.TokenList = function (input, url_or_data, settings) {
143
- //
144
- // Initialization
145
- //
146
-
147
- // Configure the data source
148
- if($.type(url_or_data) === "string" || $.type(url_or_data) === "function") {
149
- // Set the url to query against
150
- settings.url = url_or_data;
151
-
152
- // If the URL is a function, evaluate it here to do our initalization work
153
- var url = computeURL();
154
-
155
- // Make a smart guess about cross-domain if it wasn't explicitly specified
156
- if(settings.crossDomain === undefined && typeof url === "string") {
157
- if(url.indexOf("://") === -1) {
158
- settings.crossDomain = false;
159
- } else {
160
- settings.crossDomain = (location.href.split(/\/+/g)[1] !== url.split(/\/+/g)[1]);
161
- }
162
- }
163
- } else if(typeof(url_or_data) === "object") {
164
- // Set the local data to search through
165
- settings.local_data = url_or_data;
166
- }
167
-
168
- // Build class names
169
- if(settings.classes) {
170
- // Use custom class names
171
- settings.classes = $.extend({}, DEFAULT_CLASSES, settings.classes);
172
- } else if(settings.theme) {
173
- // Use theme-suffixed default class names
174
- settings.classes = {};
175
- $.each(DEFAULT_CLASSES, function(key, value) {
176
- settings.classes[key] = value + "-" + settings.theme;
177
- });
178
- } else {
179
- settings.classes = DEFAULT_CLASSES;
180
- }
181
-
182
-
183
- // Save the tokens
184
- var saved_tokens = [];
185
-
186
- // Keep track of the number of tokens in the list
187
- var token_count = 0;
188
-
189
- // Basic cache to save on db hits
190
- var cache = new $.TokenList.Cache();
191
-
192
- // Keep track of the timeout, old vals
193
- var timeout;
194
- var input_val;
195
-
196
- // Create a new text input an attach keyup events
197
- var input_box = $("<input type=\"text\" autocomplete=\"off\">")
198
- .css({
199
- outline: "none"
200
- })
201
- .attr("id", settings.idPrefix + input.id)
202
- .focus(function () {
203
- if (settings.disabled) {
204
- return false;
205
- } else
206
- if (settings.tokenLimit === null || settings.tokenLimit !== token_count) {
207
- show_dropdown_hint();
208
- }
209
- token_list.addClass(settings.classes.focused);
210
- })
211
- .blur(function () {
212
- hide_dropdown();
213
- $(this).val("");
214
- token_list.removeClass(settings.classes.focused);
215
- })
216
- .bind("keyup keydown blur update", resize_input)
217
- .keydown(function (event) {
218
- var previous_token;
219
- var next_token;
220
-
221
- switch(event.keyCode) {
222
- case KEY.LEFT:
223
- case KEY.RIGHT:
224
- case KEY.UP:
225
- case KEY.DOWN:
226
- if(!$(this).val()) {
227
- previous_token = input_token.prev();
228
- next_token = input_token.next();
229
-
230
- if((previous_token.length && previous_token.get(0) === selected_token) || (next_token.length && next_token.get(0) === selected_token)) {
231
- // Check if there is a previous/next token and it is selected
232
- if(event.keyCode === KEY.LEFT || event.keyCode === KEY.UP) {
233
- deselect_token($(selected_token), POSITION.BEFORE);
234
- } else {
235
- deselect_token($(selected_token), POSITION.AFTER);
236
- }
237
- } else if((event.keyCode === KEY.LEFT || event.keyCode === KEY.UP) && previous_token.length) {
238
- // We are moving left, select the previous token if it exists
239
- select_token($(previous_token.get(0)));
240
- } else if((event.keyCode === KEY.RIGHT || event.keyCode === KEY.DOWN) && next_token.length) {
241
- // We are moving right, select the next token if it exists
242
- select_token($(next_token.get(0)));
243
- }
244
- } else {
245
- var dropdown_item = null;
246
-
247
- if(event.keyCode === KEY.DOWN || event.keyCode === KEY.RIGHT) {
248
- dropdown_item = $(selected_dropdown_item).next();
249
- } else {
250
- dropdown_item = $(selected_dropdown_item).prev();
251
- }
252
-
253
- if(dropdown_item.length) {
254
- select_dropdown_item(dropdown_item);
255
- }
256
- }
257
- return false;
258
- break;
259
-
260
- case KEY.BACKSPACE:
261
- previous_token = input_token.prev();
262
-
263
- if(!$(this).val().length) {
264
- if(selected_token) {
265
- delete_token($(selected_token));
266
- hidden_input.change();
267
- } else if(previous_token.length) {
268
- select_token($(previous_token.get(0)));
269
- }
270
-
271
- return false;
272
- } else if($(this).val().length === 1) {
273
- hide_dropdown();
274
- } else {
275
- // set a timeout just long enough to let this function finish.
276
- setTimeout(function(){do_search();}, 5);
277
- }
278
- break;
279
-
280
- case KEY.TAB:
281
- case KEY.ENTER:
282
- case KEY.NUMPAD_ENTER:
283
- case KEY.COMMA:
284
- if(selected_dropdown_item) {
285
- add_token($(selected_dropdown_item).data("tokeninput"));
286
- hidden_input.change();
287
- return false;
288
- }
289
- break;
290
-
291
- case KEY.ESCAPE:
292
- hide_dropdown();
293
- return true;
294
-
295
- default:
296
- if(String.fromCharCode(event.which)) {
297
- // set a timeout just long enough to let this function finish.
298
- setTimeout(function(){do_search();}, 5);
299
- }
300
- break;
301
- }
302
- });
303
-
304
- // Keep a reference to the original input box
305
- var hidden_input = $(input)
306
- .hide()
307
- .val("")
308
- .focus(function () {
309
- focus_with_timeout(input_box);
310
- })
311
- .blur(function () {
312
- input_box.blur();
313
- });
314
-
315
- // Keep a reference to the selected token and dropdown item
316
- var selected_token = null;
317
- var selected_token_index = 0;
318
- var selected_dropdown_item = null;
319
-
320
- // The list to store the token items in
321
- var token_list = $("<ul />")
322
- .addClass(settings.classes.tokenList)
323
- .click(function (event) {
324
- var li = $(event.target).closest("li");
325
- if(li && li.get(0) && $.data(li.get(0), "tokeninput")) {
326
- toggle_select_token(li);
327
- } else {
328
- // Deselect selected token
329
- if(selected_token) {
330
- deselect_token($(selected_token), POSITION.END);
331
- }
332
-
333
- // Focus input box
334
- focus_with_timeout(input_box);
335
- }
336
- })
337
- .mouseover(function (event) {
338
- var li = $(event.target).closest("li");
339
- if(li && selected_token !== this) {
340
- li.addClass(settings.classes.highlightedToken);
341
- }
342
- })
343
- .mouseout(function (event) {
344
- var li = $(event.target).closest("li");
345
- if(li && selected_token !== this) {
346
- li.removeClass(settings.classes.highlightedToken);
347
- }
348
- })
349
- .insertBefore(hidden_input);
350
-
351
- // The token holding the input box
352
- var input_token = $("<li />")
353
- .addClass(settings.classes.inputToken)
354
- .appendTo(token_list)
355
- .append(input_box);
356
-
357
- // The list to store the dropdown items in
358
- var dropdown = $("<div>")
359
- .addClass(settings.classes.dropdown)
360
- .appendTo("body")
361
- .hide();
362
-
363
- // Magic element to help us resize the text input
364
- var input_resizer = $("<tester/>")
365
- .insertAfter(input_box)
366
- .css({
367
- position: "absolute",
368
- top: -9999,
369
- left: -9999,
370
- width: "auto",
371
- fontSize: input_box.css("fontSize"),
372
- fontFamily: input_box.css("fontFamily"),
373
- fontWeight: input_box.css("fontWeight"),
374
- letterSpacing: input_box.css("letterSpacing"),
375
- whiteSpace: "nowrap"
376
- });
377
-
378
- // Pre-populate list if items exist
379
- hidden_input.val("");
380
- var li_data = settings.prePopulate || hidden_input.data("pre");
381
- if(settings.processPrePopulate && $.isFunction(settings.onResult)) {
382
- li_data = settings.onResult.call(hidden_input, li_data);
383
- }
384
- if(li_data && li_data.length) {
385
- $.each(li_data, function (index, value) {
386
- insert_token(value);
387
- checkTokenLimit();
388
- });
389
- }
390
-
391
- // Check if widget should initialize as disabled
392
- if (settings.disabled) {
393
- toggleDisabled(true);
394
- }
395
-
396
- // Initialization is done
397
- if($.isFunction(settings.onReady)) {
398
- settings.onReady.call();
399
- }
400
-
401
- //
402
- // Public functions
403
- //
404
-
405
- this.clear = function() {
406
- token_list.children("li").each(function() {
407
- if ($(this).children("input").length === 0) {
408
- delete_token($(this));
409
- }
410
- });
411
- }
412
-
413
- this.add = function(item) {
414
- add_token(item);
415
- }
416
-
417
- this.remove = function(item) {
418
- token_list.children("li").each(function() {
419
- if ($(this).children("input").length === 0) {
420
- var currToken = $(this).data("tokeninput");
421
- var match = true;
422
- for (var prop in item) {
423
- if (item[prop] !== currToken[prop]) {
424
- match = false;
425
- break;
426
- }
427
- }
428
- if (match) {
429
- delete_token($(this));
430
- }
431
- }
432
- });
433
- }
434
-
435
- this.getTokens = function() {
436
- return saved_tokens;
437
- }
438
-
439
- this.toggleDisabled = function(disable) {
440
- toggleDisabled(disable);
441
- }
442
-
443
- //
444
- // Private functions
445
- //
446
-
447
- // Toggles the widget between enabled and disabled state, or according
448
- // to the [disable] parameter.
449
- function toggleDisabled(disable) {
450
- if (typeof disable === 'boolean') {
451
- settings.disabled = disable
452
- } else {
453
- settings.disabled = !settings.disabled;
454
- }
455
- input_box.prop('disabled', settings.disabled);
456
- token_list.toggleClass(settings.classes.disabled, settings.disabled);
457
- // if there is any token selected we deselect it
458
- if(selected_token) {
459
- deselect_token($(selected_token), POSITION.END);
460
- }
461
- hidden_input.prop('disabled', settings.disabled);
462
- }
463
-
464
- function checkTokenLimit() {
465
- if(settings.tokenLimit !== null && token_count >= settings.tokenLimit) {
466
- input_box.hide();
467
- hide_dropdown();
468
- return;
469
- }
470
- }
471
-
472
- function resize_input() {
473
- if(input_val === (input_val = input_box.val())) {return;}
474
-
475
- // Enter new content into resizer and resize input accordingly
476
- var escaped = input_val.replace(/&/g, '&amp;').replace(/\s/g,' ').replace(/</g, '&lt;').replace(/>/g, '&gt;');
477
- input_resizer.html(escaped);
478
- input_box.width(input_resizer.width() + 30);
479
- }
480
-
481
- function is_printable_character(keycode) {
482
- return ((keycode >= 48 && keycode <= 90) || // 0-1a-z
483
- (keycode >= 96 && keycode <= 111) || // numpad 0-9 + - / * .
484
- (keycode >= 186 && keycode <= 192) || // ; = , - . / ^
485
- (keycode >= 219 && keycode <= 222)); // ( \ ) '
486
- }
487
-
488
- // Inner function to a token to the list
489
- function insert_token(item) {
490
- var $this_token = $(settings.tokenFormatter(item));
491
- var readonly = item.readonly === true ? true : false;
492
-
493
- if(readonly) $this_token.addClass(settings.classes.tokenReadOnly);
494
-
495
- $this_token.addClass(settings.classes.token).insertBefore(input_token);
496
-
497
- // The 'delete token' button
498
- if(!readonly) {
499
- $("<span>" + settings.deleteText + "</span>")
500
- .addClass(settings.classes.tokenDelete)
501
- .appendTo($this_token)
502
- .click(function () {
503
- if (!settings.disabled) {
504
- delete_token($(this).parent());
505
- hidden_input.change();
506
- return false;
507
- }
508
- });
509
- }
510
-
511
- // Store data on the token
512
- var token_data = item;
513
- $.data($this_token.get(0), "tokeninput", item);
514
-
515
- // Save this token for duplicate checking
516
- saved_tokens = saved_tokens.slice(0,selected_token_index).concat([token_data]).concat(saved_tokens.slice(selected_token_index));
517
- selected_token_index++;
518
-
519
- // Update the hidden input
520
- update_hidden_input(saved_tokens, hidden_input);
521
-
522
- token_count += 1;
523
-
524
- // Check the token limit
525
- if(settings.tokenLimit !== null && token_count >= settings.tokenLimit) {
526
- input_box.hide();
527
- hide_dropdown();
528
- }
529
-
530
- return $this_token;
531
- }
532
-
533
- // Add a token to the token list based on user input
534
- function add_token (item) {
535
- var callback = settings.onAdd;
536
-
537
- // See if the token already exists and select it if we don't want duplicates
538
- if(token_count > 0 && settings.preventDuplicates) {
539
- var found_existing_token = null;
540
- token_list.children().each(function () {
541
- var existing_token = $(this);
542
- var existing_data = $.data(existing_token.get(0), "tokeninput");
543
- if(existing_data && existing_data.id === item.id) {
544
- found_existing_token = existing_token;
545
- return false;
546
- }
547
- });
548
-
549
- if(found_existing_token) {
550
- select_token(found_existing_token);
551
- input_token.insertAfter(found_existing_token);
552
- focus_with_timeout(input_box);
553
- return;
554
- }
555
- }
556
-
557
- // Insert the new tokens
558
- if(settings.tokenLimit == null || token_count < settings.tokenLimit) {
559
- insert_token(item);
560
- checkTokenLimit();
561
- }
562
-
563
- // Clear input box
564
- input_box.val("");
565
-
566
- // Don't show the help dropdown, they've got the idea
567
- hide_dropdown();
568
-
569
- // Execute the onAdd callback if defined
570
- if($.isFunction(callback)) {
571
- callback.call(hidden_input,item);
572
- }
573
- }
574
-
575
- // Select a token in the token list
576
- function select_token (token) {
577
- if (!settings.disabled) {
578
- token.addClass(settings.classes.selectedToken);
579
- selected_token = token.get(0);
580
-
581
- // Hide input box
582
- input_box.val("");
583
-
584
- // Hide dropdown if it is visible (eg if we clicked to select token)
585
- hide_dropdown();
586
- }
587
- }
588
-
589
- // Deselect a token in the token list
590
- function deselect_token (token, position) {
591
- token.removeClass(settings.classes.selectedToken);
592
- selected_token = null;
593
-
594
- if(position === POSITION.BEFORE) {
595
- input_token.insertBefore(token);
596
- selected_token_index--;
597
- } else if(position === POSITION.AFTER) {
598
- input_token.insertAfter(token);
599
- selected_token_index++;
600
- } else {
601
- input_token.appendTo(token_list);
602
- selected_token_index = token_count;
603
- }
604
-
605
- // Show the input box and give it focus again
606
- focus_with_timeout(input_box);
607
- }
608
-
609
- // Toggle selection of a token in the token list
610
- function toggle_select_token(token) {
611
- var previous_selected_token = selected_token;
612
-
613
- if(selected_token) {
614
- deselect_token($(selected_token), POSITION.END);
615
- }
616
-
617
- if(previous_selected_token === token.get(0)) {
618
- deselect_token(token, POSITION.END);
619
- } else {
620
- select_token(token);
621
- }
622
- }
623
-
624
- // Delete a token from the token list
625
- function delete_token (token) {
626
- // Remove the id from the saved list
627
- var token_data = $.data(token.get(0), "tokeninput");
628
- var callback = settings.onDelete;
629
-
630
- var index = token.prevAll().length;
631
- if(index > selected_token_index) index--;
632
-
633
- // Delete the token
634
- token.remove();
635
- selected_token = null;
636
-
637
- // Show the input box and give it focus again
638
- focus_with_timeout(input_box);
639
-
640
- // Remove this token from the saved list
641
- saved_tokens = saved_tokens.slice(0,index).concat(saved_tokens.slice(index+1));
642
- if(index < selected_token_index) selected_token_index--;
643
-
644
- // Update the hidden input
645
- update_hidden_input(saved_tokens, hidden_input);
646
-
647
- token_count -= 1;
648
-
649
- if(settings.tokenLimit !== null) {
650
- input_box
651
- .show()
652
- .val("");
653
- focus_with_timeout(input_box);
654
- }
655
-
656
- // Execute the onDelete callback if defined
657
- if($.isFunction(callback)) {
658
- callback.call(hidden_input,token_data);
659
- }
660
- }
661
-
662
- // Update the hidden input box value
663
- function update_hidden_input(saved_tokens, hidden_input) {
664
- var token_values = $.map(saved_tokens, function (el) {
665
- if(typeof settings.tokenValue == 'function')
666
- return settings.tokenValue.call(this, el);
667
-
668
- return el[settings.tokenValue];
669
- });
670
- hidden_input.val(token_values.join(settings.tokenDelimiter));
671
-
672
- }
673
-
674
- // Hide and clear the results dropdown
675
- function hide_dropdown () {
676
- dropdown.hide().empty();
677
- selected_dropdown_item = null;
678
- }
679
-
680
- function show_dropdown() {
681
- dropdown
682
- .css({
683
- position: "absolute",
684
- top: $(token_list).offset().top + $(token_list).outerHeight(),
685
- left: $(token_list).offset().left,
686
- width: $(token_list).outerWidth(),
687
- 'z-index': settings.zindex
688
- })
689
- .show();
690
- }
691
-
692
- function show_dropdown_searching () {
693
- if(settings.searchingText) {
694
- dropdown.html("<p>"+settings.searchingText+"</p>");
695
- show_dropdown();
696
- }
697
- }
698
-
699
- function show_dropdown_hint () {
700
- if(settings.hintText) {
701
- dropdown.html("<p>"+settings.hintText+"</p>");
702
- show_dropdown();
703
- }
704
- }
705
-
706
- var regexp_special_chars = new RegExp('[.\\\\+*?\\[\\^\\]$(){}=!<>|:\\-]', 'g');
707
- function regexp_escape(term) {
708
- return term.replace(regexp_special_chars, '\\$&');
709
- }
710
-
711
- // Highlight the query part of the search term
712
- function highlight_term(value, term) {
713
- return value.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)(" + regexp_escape(term) + ")(?![^<>]*>)(?![^&;]+;)", "gi"), "<b>$1</b>");
714
- }
715
-
716
- function find_value_and_highlight_term(template, value, term) {
717
- return template.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)(" + regexp_escape(value) + ")(?![^<>]*>)(?![^&;]+;)", "g"), highlight_term(value, term));
718
- }
719
-
720
- // Populate the results dropdown with some results
721
- function populate_dropdown (query, results) {
722
- if(results && results.length) {
723
- dropdown.empty();
724
- var dropdown_ul = $("<ul>")
725
- .appendTo(dropdown)
726
- .mouseover(function (event) {
727
- select_dropdown_item($(event.target).closest("li"));
728
- })
729
- .mousedown(function (event) {
730
- add_token($(event.target).closest("li").data("tokeninput"));
731
- hidden_input.change();
732
- return false;
733
- })
734
- .hide();
735
-
736
- if (settings.resultsLimit && results.length > settings.resultsLimit) {
737
- results = results.slice(0, settings.resultsLimit);
738
- }
739
-
740
- $.each(results, function(index, value) {
741
- var this_li = settings.resultsFormatter(value);
742
-
743
- this_li = find_value_and_highlight_term(this_li ,value[settings.propertyToSearch], query);
744
-
745
- this_li = $(this_li).appendTo(dropdown_ul);
746
-
747
- if(index % 2) {
748
- this_li.addClass(settings.classes.dropdownItem);
749
- } else {
750
- this_li.addClass(settings.classes.dropdownItem2);
751
- }
752
-
753
- if(index === 0) {
754
- select_dropdown_item(this_li);
755
- }
756
-
757
- $.data(this_li.get(0), "tokeninput", value);
758
- });
759
-
760
- show_dropdown();
761
-
762
- if(settings.animateDropdown) {
763
- dropdown_ul.slideDown("fast");
764
- } else {
765
- dropdown_ul.show();
766
- }
767
- } else {
768
- if(settings.noResultsText) {
769
- dropdown.html("<p>"+settings.noResultsText+"</p>");
770
- show_dropdown();
771
- }
772
- }
773
- }
774
-
775
- // Highlight an item in the results dropdown
776
- function select_dropdown_item (item) {
777
- if(item) {
778
- if(selected_dropdown_item) {
779
- deselect_dropdown_item($(selected_dropdown_item));
780
- }
781
-
782
- item.addClass(settings.classes.selectedDropdownItem);
783
- selected_dropdown_item = item.get(0);
784
- }
785
- }
786
-
787
- // Remove highlighting from an item in the results dropdown
788
- function deselect_dropdown_item (item) {
789
- item.removeClass(settings.classes.selectedDropdownItem);
790
- selected_dropdown_item = null;
791
- }
792
-
793
- // Do a search and show the "searching" dropdown if the input is longer
794
- // than settings.minChars
795
- function do_search() {
796
- var query = input_box.val();
797
-
798
- if(query && query.length) {
799
- if(selected_token) {
800
- deselect_token($(selected_token), POSITION.AFTER);
801
- }
802
-
803
- if(query.length >= settings.minChars) {
804
- show_dropdown_searching();
805
- clearTimeout(timeout);
806
-
807
- timeout = setTimeout(function(){
808
- run_search(query);
809
- }, settings.searchDelay);
810
- } else {
811
- hide_dropdown();
812
- }
813
- }
814
- }
815
-
816
- // Do the actual search
817
- function run_search(query) {
818
- var cache_key = query + computeURL();
819
- var cached_results = cache.get(cache_key);
820
- if(cached_results) {
821
- populate_dropdown(query, cached_results);
822
- } else {
823
- // Are we doing an ajax search or local data search?
824
- if(settings.url) {
825
- var url = computeURL();
826
- // Extract exisiting get params
827
- var ajax_params = {};
828
- ajax_params.data = {};
829
- if(url.indexOf("?") > -1) {
830
- var parts = url.split("?");
831
- ajax_params.url = parts[0];
832
-
833
- var param_array = parts[1].split("&");
834
- $.each(param_array, function (index, value) {
835
- var kv = value.split("=");
836
- ajax_params.data[kv[0]] = kv[1];
837
- });
838
- } else {
839
- ajax_params.url = url;
840
- }
841
-
842
- // Prepare the request
843
- ajax_params.data[settings.queryParam] = query;
844
- ajax_params.type = settings.method;
845
- ajax_params.dataType = settings.contentType;
846
- if(settings.crossDomain) {
847
- ajax_params.dataType = "jsonp";
848
- }
849
-
850
- // Attach the success callback
851
- ajax_params.success = function(results) {
852
- if($.isFunction(settings.onResult)) {
853
- results = settings.onResult.call(hidden_input, results);
854
- }
855
- cache.add(cache_key, settings.jsonContainer ? results[settings.jsonContainer] : results);
856
-
857
- // only populate the dropdown if the results are associated with the active search query
858
- if(input_box.val() === query) {
859
- populate_dropdown(query, settings.jsonContainer ? results[settings.jsonContainer] : results);
860
- }
861
- };
862
-
863
- // Make the request
864
- $.ajax(ajax_params);
865
- } else if(settings.local_data) {
866
- // Do the search through local data
867
- var results = $.grep(settings.local_data, function (row) {
868
- return row[settings.propertyToSearch].toLowerCase().indexOf(query.toLowerCase()) > -1;
869
- });
870
-
871
- if($.isFunction(settings.onResult)) {
872
- results = settings.onResult.call(hidden_input, results);
873
- }
874
- cache.add(cache_key, results);
875
- populate_dropdown(query, results);
876
- }
877
- }
878
- }
879
-
880
- // compute the dynamic URL
881
- function computeURL() {
882
- var url = settings.url;
883
- if(typeof settings.url == 'function') {
884
- url = settings.url.call(settings);
885
- }
886
- return url;
887
- }
888
-
889
- // Bring browser focus to the specified object.
890
- // Use of setTimeout is to get around an IE bug.
891
- // (See, e.g., http://stackoverflow.com/questions/2600186/focus-doesnt-work-in-ie)
892
- //
893
- // obj: a jQuery object to focus()
894
- function focus_with_timeout(obj) {
895
- setTimeout(function() { obj.focus(); }, 50);
896
- }
897
-
898
- };
899
-
900
- // Really basic cache for the results
901
- $.TokenList.Cache = function (options) {
902
- var settings = $.extend({
903
- max_size: 500
904
- }, options);
905
-
906
- var data = {};
907
- var size = 0;
908
-
909
- var flush = function () {
910
- data = {};
911
- size = 0;
912
- };
913
-
914
- this.add = function (query, results) {
915
- if(size > settings.max_size) {
916
- flush();
917
- }
918
-
919
- if(!data[query]) {
920
- size += 1;
921
- }
922
-
923
- data[query] = results;
924
- };
925
-
926
- this.get = function (query) {
927
- return data[query];
928
- };
929
- };
930
- }(jQuery));