Crawlicious | tools for web business

Archive for January 2010

I am using jquery with the Devbridge autocomplete plugin.  It is an awesome tool.  Unfortunately we had a bug reported that on IE6 the autocomplete box does not correctly cover up the other controls on the page.  There are select boxes below the field with the drop down and when everything else is covered up, these select boxes stick out like a sore thumb.

Normally you would use the bgiframe plugin for jquery to address this problem, but in this case we don’t have a reference to the dropdown list once it is filled in from the ajax call.  So, my solution was to add a simple callback to the autocomplete plugin that is fired off after the list is populated and made visible.  That gives me the option that simply takes the list container and calls bgiframe on it.  And viola!  My dropdown list covers up all the controls underneath, even the select lists.

Here is a patch if you would like to patch the autocomplete plugin.  Note, it also contains a fix from my last post about using multiple fields as input (the Devbridge autocomplete part is at the bottom of the post).

--- jquery.autocomplete.js  2009-09-27 23:15:14.000000000 -0600
+++ ../jquery.autocomplete.js   2010-01-29 15:29:14.000000000 -0700
@@ -230,6 +230,9 @@
     },^M
     ^M
     getSuggestions: function(q) {^M
+      if (this.options.noCaching) {^M
+        this.clearCache();^M
+      }^M
       var cr, me;^M
       cr = this.isLocal ? this.getSuggestionsLocal(q) : this.cachedResponse[q];^M
       if (cr && $.isArray(cr.suggestions)) {^M
@@ -280,6 +283,7 @@
       }^M
       this.enabled = true;^M
       this.container.show();^M
+      if ($.isFunction(me.options.onListShow)) { me.options.onListShow(this.container); }^M
     },^M
 ^M
     processResponse: function(text) {^M

Download the actual patch right here!  jquery.autocomplete.js.patch

Remember, to patch your file, simply cd to where your jquery.autocomplete.js file resides (and copy in this patch to that directory to a file called jquery.autocomplete.js.patch) and run this command


patch jquery.autocomplete.js < jquery.autocomplete.js.patch

Now, once you have that file patched, you can do this sort of thing with your autocomplete options.


$("input[name*=some_name], input[name*=some_other_name]").each(function(i) {
$(this).autocomplete(
{
serviceUrl:baseURL + '/lib/dostuffremotely',
minChars:3,
width:500,
maxHeight:400,
zIndex: 9876,
deferRequestBy: 0, //milliseconds
params: {
'prefix':'xyz',
'column':'abc'
},
onListShow: function(container) { container.bgiframe(); }, // LOOK HERE, THIS IS NEW!!!
onSelect: function(value, data){  // "this" is NOT defined here
// handle onselect
}
}
);

Happy jquerying!

Eric

http://www.devbridge.com/projects/autocomplete/jquery/local/downloads/jquery.autocomplete-
http://www.devbridge.com/projects/autocomplete/jquery/local/downloads/jquery.autocomplete-1.1.zip

, Hide

This is in response to a question asked about a jquery autocomplete plugin.

stackoverflow question

The question was, if you are using this jquery autocomplete plugin how do you get the .autocomplete function to include other fields so that you can have a context type of search.  One person (bendewey) answered that you can do the following.

var selectedCategory = $('.categories').val();
var query = '';
if (selectedCategory !== 0)
{
query = '?category=' + selectedCategory;
}
$("#suggest4").autocomplete('search_service.svc' + query, {
// options
});

This is 1/2 correct.  The problem is that when .autocomplete() is called, the url + query are evaluated immediately which means that the current (at time of page loading most likely) selected category value will ALWAYS be used when autocomplete is called.  That means that if the user selected a different category, the new value will not be passed with the query.  Here is a patch to the autocomplete code that will fix it.  After running the patch, you will be able to pass a function to your .autocomplete call (instead of a string url) and then each time autocomplete runs, the function will be run to create the right params.

to run patch:
1. cd to the directory where your jquery.autocomplete.js file exists

2. copy the patch file to a file called jquery.autocomplete.js.patch (in the above mentioned directory)
3. run patch < jquery.autocomplete.js.patch

to use the patch:
do what bendewey said above, except for you need to make the 1st arg of .autocomplete to be a function that returns the proper query, like this…

$("#suggest4").autocomplete(function() {
 var selectedCategory = $('.categories').val();
 var query = '';
 if (selectedCategory !== 0)
 {
   query = '?category=' + selectedCategory;
 }
 return 'search_service.svc' + query; }, {
 // options
 }
);

Here is the patch (you can download the file below):


--- jquery.autocomplete.js.orig 2010-01-15 11:00:55.000000000 -0700
+++ jquery.autocomplete.js  2010-01-15 11:04:02.000000000 -0700
@@ -14,7 +14,7 @@

 $.fn.extend({
 autocomplete: function(urlOrData, options) {
-       var isUrl = typeof urlOrData == "string";
+       var isUrl = typeof urlOrData == "string" || typeof urlOrData == "function";
 options = $.extend({}, $.Autocompleter.defaults, {
 url: isUrl ? urlOrData : null,
 data: isUrl ? null : urlOrData,
@@ -346,10 +346,14 @@
 term = term.toLowerCase();
 var data = cache.load(term);
 // recieve the cached data
+        var url = options.url;
+        if (typeof url == "function") {
+            url = options.url();
+        }
 if (data && data.length) {
 success(term, data);
 // if an AJAX url has been supplied, try loading the data now
-       } else if( (typeof options.url == "string") && (options.url.length > 0) ){
+       } else if( (typeof url == "string") && (url.length > 0) ){

 var extraParams = {
 timestamp: +new Date()
@@ -364,14 +368,16 @@
 // limit abortion to this input
 port: "autocomplete" + input.name,
 dataType: options.dataType,
-               url: options.url,
+               url: url,
 data: $.extend({
 q: lastWord(term),
 limit: options.max
 }, extraParams),
 success: function(data) {
 var parsed = options.parse && options.parse(data) || parse(data);
-                   cache.add(term, parsed);
+                    if (typeof options.url != "function") {
+                        cache.add(term, parsed);
+                    }
 success(term, parsed);
 }
 });

You can also download the patch file here:  jquery.autocomplete.js.patch

Now, what if you are using this autocomplete from Devbridge?  You can almost do it out of the box, here is a code sample.


$("input[name*=phone_number]").each(function(i) {
 var prefix = this.id.replace(/\.[^.]*$/, "");
 $(this).autocomplete(
 {
 serviceUrl:baseURL + '/lib/findUsers',
 zIndex: 9999,
 deferRequestBy: 0, //milliseconds
 noCaching: true,
 params: {
 'area':function() { return $(jq(prefix + ".area_id")).val(); },
 'prefix':prefix
 },
 onSelect: function(value, data){  // NOTE: 'this' is NOT defined correctly here
 // do stuff with data
 }
 }
 );
 });

You will notice that I included a parameter that isn’t supported, that is the noCaching parameter.  I had this working pretty good without it, except if you changed the non-autocomplete field (in this case area code), and you go back to the auto field and fail to find something, that is cached with the query, so when you change the area code, you get stuck because the query field got cached, and auto thinks that it should not try again.  That is why I made this tiny patch to this version of autocomplete.


Index: jquery.autocomplete.js
===================================================================
RCS file: /opt/Repository/MobilSense/MobilSentry/Products/MobilSentry/Src/CSS/share/assets/jquery.autocomplete.js,v
retrieving revision 1.1
diff -u -r1.1 jquery.autocomplete.js
--- jquery.autocomplete.js  10 Jan 2010 06:46:45 -0000  1.1
+++ jquery.autocomplete.js  15 Jan 2010 23:20:55 -0000
@@ -230,6 +230,9 @@
 },^M
 ^M
 getSuggestions: function(q) {^M
+      if (this.options.noCaching) {^M
+        this.clearCache();^M
+      }^M
 var cr, me;^M
 cr = this.isLocal ? this.getSuggestionsLocal(q) : this.cachedResponse[q];^M
 if (cr && $.isArray(cr.suggestions)) {^M

And you can download it jquery.autocomplete.js.patch.

UPDATE

————————-

Latest patched version of the devbridge autocomplete file…  jquery.autocomplete.js

, Hide

Find it!

Theme Design by devolux.org