65

I'm using the JQuery Autocomplete in one of my forms.

The basic form selects products from my database. This works great, but I'd like to further develop so that only products shipped from a certain zipcode are returned. I've got the backend script figured out. I just need to work out the best way to pass the zipcode to this script.

This is how my form looks.

<form>

<select id="zipcode">

<option value="2000">2000</option>
<option value="3000">3000</option>
<option value="4000">4000</option>

</select>

<input type="text" id="product"/>

<input type="submit"/>

</form>

And here is the JQuery code:

$("#product").autocomplete
({
     source:"product_auto_complete.php?postcode=" + $('#zipcode').val() +"&",
     minLength: 2,
     select: function(event, ui){

                             //action

                                 }
});

This code works to an extent. But only returns the first zipcode value regardless of which value is actually selected. I guess what's happening is that the source URL is primed on page load rather than when the select menu is changed. Is there a way around this? Or is there a better way overall to achieve the result I'm after?

Nick Craver
  • 623,446
  • 136
  • 1,297
  • 1,155
matt
  • 821
  • 1
  • 8
  • 12

8 Answers8

104

You need to use a different approach for the source call, like this:

$("#product").autocomplete({
  source: function(request, response) {
    $.getJSON("product_auto_complete.php", { postcode: $('#zipcode').val() }, 
              response);
  },
  minLength: 2,
  select: function(event, ui){
    //action
  }
});

This format lets you pass whatever the value is when it's run, as opposed to when it's bound.

Nick Craver
  • 623,446
  • 136
  • 1,297
  • 1,155
  • Hmmm. I can't seem to make it work using this method. Although it would be great if i could as it seems like a more elegant way of approaching the problem. Does the JSON data need to be structured differently? Do I still use $_GET['postcode'] && $_GET['term'] in my source file? – matt Sep 13 '10 at 01:58
  • 24
    @matt - You'll just be using `$_GET['postcode']` with the above code...if you want term on there, add it in by using this for the data argument: `{ term: request.term, postcode: $('#zipcode').val() }` – Nick Craver Sep 13 '10 at 02:21
  • 2
    @Nick Still having trouble getting it working. I've made the change, but the autocomplete fails to materialise. Jquery is very new to me, so I'm not sure how to debug, but it seems to stop all code from my javascript file from working. I'm not sure what might be out of place, but the "request.term" is new to me.Just to clarify, this is the "term" that autocomplete creates as you type, right? – matt Sep 13 '10 at 09:06
  • @matt - Correct that's where it comes from...the error was a missing comma after the `source` option in the above code [see here](http://stackoverflow.com/posts/3694296/revisions), sorry! The console is the best place for debugging all JS errors, either Firebug or Chrome include excellent consoles for this. – Nick Craver Sep 13 '10 at 09:39
  • @Nick - Hi Nick, Hope you don't mind me asking but; Are you able to explain, or point me in the right direction to understanding, how the function(request, response) changes it from being when it's bound to being when it's run? - Also: is the response some type of output parameter, and where does the request parameter come from/get used? (I'm pretty new to this stuff atm). Cheers. – Zack Sep 21 '10 at 16:05
  • 1
    @King - `response` is a function passed in when it's called, it's a callback function that itself takes a single parameter, the response text or data...that function sticks the data in the autocomplete widget. `request` is also provided, it's an object with a `term` property which is what's currently types in the box, it's passed in when the widget calls this method. – Nick Craver Sep 21 '10 at 16:10
  • 2
    Seems to be the cleanest method. I might recommend mentioning `term: request.term` in the answer itself, rather than solely as a comment. – primo Aug 01 '19 at 05:13
  • As mentioned by Nick, the "term: request.term" expression needs to be included within the curly brackets, otherwise you would not get a response for your search term, which is the whole purpose of the autocomplete function. – Luftwaffle Mar 28 '22 at 13:29
37

This is not to complicated men:

$(document).ready(function() {
src = 'http://domain.com/index.php';

// Load the cities straight from the server, passing the country as an extra param
$("#city_id").autocomplete({
    source: function(request, response) {
        $.ajax({
            url: src,
            dataType: "json",
            data: {
                term : request.term,
                country_id : $("#country_id").val()
            },
            success: function(data) {
                response(data);
            }
        });
    },
    min_length: 3,
    delay: 300
});
});
Daniel Kennedy
  • 708
  • 11
  • 18
9
jQuery("#whatJob").autocomplete(ajaxURL,{
    width: 260,
    matchContains: true,
    selectFirst: false,
    minChars: 2,
    extraParams: {  //to pass extra parameter in ajax file.
        "auto_dealer": "yes",
    },
});
Vishal Tanna
  • 1,165
  • 2
  • 12
  • 36
Bharat Parmar
  • 1,842
  • 2
  • 18
  • 22
6

I believe you are correct in thinking your call to $("#product").autocomplete is firing on page load. Perhaps you can assign an onchange() handler to the select menu:

$("#zipcode").change(resetAutocomplete);

and have it invalidate the #product autocomplete() call and create a new one.

function resetAutocomplete() {
    $("#product").autocomplete("destroy");
    $("#product").autocomplete({
         source:"product_auto_complete.php?postcode=" + $('#zipcode').val(),
         minLength: 2,
         select: function(event, ui){... }
    });
}

You may want your resetAutocomplete() call to be a little smarter -- like checking if the zip code actually differs from the last value -- to save a few server calls.

Paul Schreiber
  • 12,531
  • 4
  • 41
  • 63
  • Destroying the autocomplete widget and recreating it is *tremendously* wasteful, you should use the `source` argument as it was intended... – Nick Craver Sep 13 '10 at 09:40
  • @Footniko once loaded, I need to recreate it to change values, I'm using an extraParams and it doesn't update its value without doing this! – Cirelli94 Oct 17 '17 at 08:29
3

This work for me. Override the event search:

jQuery('#Distribuidor_provincia_nombre').autocomplete({
    'minLength':0,
    'search':function(event,ui){
        var newUrl="/conf/general/provincias?pais="+$("#Distribuidor_pais_id").val();
        $(this).autocomplete("option","source",newUrl)
    },
    'source':[]
});
biegleux
  • 13,179
  • 11
  • 45
  • 52
Knito Auron
  • 429
  • 4
  • 7
  • Great, simple solution for setting the GET vars on the source url at the time of the search, not on page load. So much easier to read than having an AJAX call in the source function – ransomweaver Jun 06 '14 at 19:54
1

Hope this one will help someone:

$("#txt_venuename").autocomplete({
    source: function(request, response) {
    $.getJSON('<?php echo base_url(); ?>admin/venue/venues_autocomplete', 
        { 
            user_id: <?php echo $user_param_id; ?>, 
            term: request.term 
        }, 
      response);
    },
    minLength: 3,
    select: function (a, b) {            
        var selected_venue_id = b.item.v_id;
        var selected_venue_name = b.item.label;            
        $("#h_venueid").val(selected_venue_id);
        console.log(selected_venue_id);            
    }
});

The default 'term' will be replaced by the new parameters list, so you will require to add again.

Paul Chu
  • 1,249
  • 3
  • 19
  • 27
Sanjoy
  • 51
  • 6
0
$('#txtCropname').autocomplete('Handler/CropSearch.ashx', {
    extraParams: {
        test: 'new'
    }
});
Fakhruddin Ujjainwala
  • 2,493
  • 17
  • 26
0
$('#product').setOptions({
    extraParams: {
        extra_parameter_name_to_send: function(){
            return $("#source_of_extra_parameter_name").val();
        }
    }
})
Roman Losev
  • 1,911
  • 19
  • 26