I am working on autocomplete component from jquery UI. Though my auto complete working fine but If I type suggested letter "I" it was showing all the list which is available from json data where i need only the relevant letter for example if I type letter I "India", Indonesia etc,. And I need to show only max 10 values in the list. Here I have updated the latest code I am trying to do the slice in the autocomplete and i am trying to getting the same value in the next text box.
Here is the current jquery code
$("#ipt_Countryres").autocomplete({
source: function( request, response ) {
var regex = new RegExp(request.term, 'i');
//var filteredArray = filteredArray.slice(0,10);
$.ajax({
url: "json/countries.json",
dataType: "json",
data: {term: request.term},
success: function(data) {
response($.map(data, function(item) {
if(regex.test(item.label)){
return {
id: item.id,
label: item.label,
value: item.value
};
}
}));
},
minlength:2,
select: function (event, ui) {
$("#get_country").val(ui.item.label);
}
});
}
});
Here is the HTML Code
<input type="text" id="ipt_Countryres" name="ipt_Countryres" class="ipt_Field"/>
<input type="text" class="ipt_Field" id="get_country" name="get_country"/ disabled>
Here is my sample JSON data
[
{
"value":"Afghanistan",
"label":"Afghanistan",
"id":"AF"
},
{
"value":"Åland Islands ",
"label":"Åland Islands",
"id":"AX"
},
{
"value":"Albania ",
"label":"Albania",
"id":"AL"
},
{
"value":"Algeria ",
"label":"Algeria",
"id":"DZ"
},
{
"value":"American Samoa ",
"label":"American Samoa",
"id":"AS"
},
{
"value":"AndorrA ",
"label":"AndorrA",
"id":"AD"
},
{
"value":"Angola ",
"label":"Angola",
"id":"AO"
},
{
"value":"Anguilla ",
"label":"Anguilla",
"id":"AI"
},
{
"value":"Antarctica ",
"label":"Antarctica",
"id":"AQ"
},
{
"value":"Antigua and Barbuda ",
"label":"Antigua and Barbuda",
"id":"AG"
}]
Kindly please help me.
Thank in advance
Mahadevan
Try this:
var orignalArray = [
{
"id":"Afghanistan",
"label":"Afghanistan",
"value":"AF"
},
{
"id":"Åland Islands ",
"label":"Åland Islands",
"value":"AX"
},
{
"id":"Albania ",
"label":"Albania",
"value":"AL"
}]
$("#ipt_Countryres").autocomplete({
minLength:1,
source: function(request, response) {
var filteredArray = $.map(orignalArray, function(item) {
if( item.id.startsWith(request.term)){
return item;
}
else{
return null;
}
});
filteredArray = filteredArray.slice(0,10);
response(filteredArray);
},
select: function(event, ui) {
event.preventDefault();
// Prevent value from being put in the input:
$('#ipt_Countryres').val(ui.item.label);
$('#get_country').val(ui.item.label);
// Set the next input's value to the "value" of the item.
},
focus: function(event, ui) {
event.preventDefault();
$('#ipt_Countryres').val(ui.item.label);
}
});
<link href="http://api.jqueryui.com/jquery-wp-content/themes/jquery/css/base.css" rel="stylesheet"/>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.0/jquery.min.js"></script>
<script src="https://code.jquery.com/ui/1.8.24/jquery-ui.min.js"></script>
<input type="text" id="ipt_Countryres" name="ipt_Countryres" class="ipt_Field"/>
<input type="text" class="ipt_Field" id="get_country" name="get_country"/ disabled>
Try to add below code for filtering the values with start with regex,
$.ui.autocomplete.filter = function (array, term) {
var matcher = new RegExp("^" + $.ui.autocomplete.escapeRegex(term), "i");
return $.grep(array, function (value) {
return matcher.test(value.label || value.value || value);
});
};
See more jqueryui-autocomplete-filter-words-starting-with-term
You can reduce the minLength for getting more results:
$("#ipt_Countryres").autocomplete({
source: country_list,
minLength: 3,
max:10,
select: function (event, ui) {
// Prevent value from being put in the input:
$('#ipt_Countryres').val(ui.item.label);
$('#get_country').val(ui.item.label);
// Set the next input's value to the "value" of the item.
}
});
Please find below the running code :
JS Fiddle : http://jsfiddle.net/vafus4qb/
Thank you so much for your suggestion.
Here is my final output which i get right now.
$("#ipt_Countryres").autocomplete({
highlightClass: "bold",
source: function( request, response ) {
var regex = new RegExp(request.term, 'i');
//var filteredArray = filteredArray.slice(0,10);
$.ajax({
url: "json/countries.json",
dataType: "json",
data: {term: request.term},
success: function(data) {
response($.map(data, function(item) {
if(regex.test(item.label)){
return {
id: item.id,
label: item.label,
value: item.value
};
}
}));
}
});
},
minlength:3,
select: function (event, ui) {
$("#get_country").val(ui.item.label);
}
});
Thanks & Regards
Mahadevan
Related
newbie here
first, my english is not good enough to describe the problem that i'm facing right now, so consider to see my code below
$('#selectOriginAirport, #selectDestinationAirport').select2({
placeholder: 'Select Airport',
ajax: {
url: '{{url('get-airports')}}',
dataType: 'json',
delay: 250,
data: function(params){
return { keyword: params.term };
},
processResults: function(datas, params) {
return {
results: $.map(datas.data, function(item) {
return {
text: item.cityName + ' - '+item.airportName + ' ('+item.airportCode+')',
id: item.airportCode+'|'+item.cityName,
lat: item.airportLatitude,
lon: item.airportLongitude
}
})
};
},
cache: true
},
escapeMarkup: function (markup) {
// console.log('markup >>> ' + markup);
return markup;
},
minimumInputLength: 3,
templateResult: function(data) {
// console.log('data >>> ' + data);
if(data.loading) {
return data.text;
}
var markup = '<p>'+data.text+'</p>';
return markup;
},
templateSelection: function(data) {
console.log(data);
if($(this).is('#selectOriginAirport')){
console.log('pepaya');
$("[name='flightOriginLat']").val(data.lat);
$("[name='flightOriginLon']").val(data.lon);
}
if($(this).is('#selectDestinationAirport')){
console.log('kates');
$("[name='flightDestinationLat']").val(data.lat);
$("[name='flightDestinationLon']").val(data.lon);
// }
return data.airportName || data.text;
}
});
first take a look that i fire select2 by #selectOriginAirport and selectDestinationAirport
the problem is i need to make a conditional on the templateSelection function but its not work, the result is none of that 2 logical is executed
thats the problem i need to solve i wish you get what i mean
Thanks in advance
I checked the source code for select2 and it looks like select2 does pass the container as the second parameter in the templateSelection option. Here's the relevant snippet from the select2.js
SingleSelection.prototype.display = function (data, container) {
var template = this.options.get('templateSelection');
var escapeMarkup = this.options.get('escapeMarkup');
return escapeMarkup(template(data, container));
};
Using that and JSFiddle's /echo/json as a sample AJAX, I've created a working snippet:
http://jsfiddle.net/shashank2104/ozy16L8s/2/
Relevant code:
templateSelection: function(selection,inst) {
if(inst && inst.length) {
return inst.attr('id') === 'select2-user-email-address-container' ? selection.email : selection.id;
}
}
Based on the container ID, the appropriate attribute can be chosen. Hope this helps.
I have a cascade Select2 ddl and when I select the master ddl, I populate the Detail ddl without no problem. On the other hand, when I select another item on master and then click the detail, at the first time the detail ddl lists the previous items just a miliseconds. So, I need to clear all of the list items besides the selected item when the main ddl's selected index changed. Is it possible? I have tried to all of the solution methods below, but they only clear the selected item. Any idea?
$('#ProjectId').select2('data', null);
$('#ProjectId').select2('data', { id: null, text: null })
$('#ProjectId').empty();
$('#ProjectId').val(null).trigger("change");
$("#ProjectId").remove();
$('#ProjectId').val('').trigger('change');
#Html.DropDownListFor(m => m.ProjectId, Enumerable.Empty<SelectListItem>(), "Select")
$(document).ready(function () {
var issueType = $("#ProjectId");
issueType.select2({
allowClear: true,
ajax: {
url: '/Controller/GetProjects',
dataType: 'json',
delay: 250,
data: function (params) {
return {
query: params.term, //search term
page: params.page,
id: selectedMasterId
};
},
processResults: function (data, page) {
var newData = [];
$.each(data, function (index, item) {
newData.push({
id: item.Id,
text: item.Description
});
});
return { results: newData };
},
cache: true
},
escapeMarkup: function (markup) { return markup; }, // let our custom formatter work
});
});
$('#MasterId').change(function () {
selectedMasterId = $(this).val();
$('#ProjectId').select2('val', '');
$('#ProjectId').select2('data', null);
}
});
$('#id').empty().trigger("change");
Where '#id' is the jQuery selector for your select2 element.
On the select element put onchange="removeOthers(this)" in js code write this function:
function removeOthers(that){
$('option', that).not(':eq(0), :selected').remove();
//now refresh your select2
}
The scenario is, I need to append a value (a selected Value) to select2 by just clicking a button. What happen is if I click my button, the other values I selected are gone/cleared.
Only 1 value is selected which is the value in my button function. I could select multiple values when typing directly to my select2 textbox, but then if i clicked the button, its value doesn't add to select2.
How do i append a value or push an additional value to data already selected in select2 on my click Button? a new value should be added to select2 selected values everytime I click the button.
I hope my code below, and my description to what im looking for kinda help you guys. Thank you.
I'm using Northwind DataBase, for testing it. (Robert King is under Employee Table)
<input type="button" onclick="Passvalue();"/>
<input type="text" id="eq" name="eq" style="width: 200px;" />
<script>
$(function () {
$("#eq").select2({
minimumInputLength: 3,
multiple: true,
ajax: {
url: '/Employee/GetAllEmployees/',
dataType: 'json',
type: "GET",
data: function (searhTerm) {
return { query: searhTerm };
},
results:
function (data) {
return { results: data};
},
},
initSelection: function (element, callback) {
var id=$(element).val(); //element value will be 'Robert';
if (id!=="") {
$.ajax('/Employee/GetAllEmployees/', {
data: {
query: id
},
dataType: "json",
type: "GET",
}).done(function(data) { callback(data); });
}
},
createSearchChoice: function (term) {
return {id: term, text: term + ' (new)', title: term };
},
formatResult: FormatContact,
formatSelection: FormatContactSelection,
escapeMarkup: function(m) {
return m;
}
});
});
function FormatContact(contact) {
return contact.text + " (" + contact.title + ")";
}
function FormatContactSelection(contact) {
return " "+ contact.text;
}
function Passvalue() {
var test2 = "Robert"; //just an example, value 'Robert' to be passed on select2 for query
$('#eq').select2("val", [test2]);
}
</script>
My Action Controller:
public ActionResult GetAllEmployees(string query)
{
var db = new Employee().GetAllEmployees(query).
ToList();
return Json(db, JsonRequestBehavior.AllowGet);
}
BL:
public IQueryable<Object> GetAllEmployees(string search)
{
var ctx = new NorthwindEntities();
var dbQuery =
(from i in ctx.Employees
where i.FirstName.Contains(search) || i.LastName.Contains(search)
select new
{
id = i.EmployeeID,
text = i.FirstName + " " + i.LastName,
title = i.Title
});
return dbQuery;
}
Instead of using "val" use "data". Something like this
this.$("#yourSelector").select2("data", [{ id: 1, text: "Some Text" },{ id: 2, text: "Some Other Text" }]);
So something like this would work for you...
var existingData = this.$("#yourSelector").select2("data");
existingData.push({ id: 11, text: "Some Text" });
this.$("#yourSelector").select2("data", existingData);
P.S : I have not tested the above code.
I have an input (textarea) that has Select2's tags applied to it. So when a user types in the name of an item that exists in my data base, it shows a list of matching items and the user can select one and a tag is created.
Here is my code so far for basic tag functionality:
$('#usualSuppliers').select2({
placeholder: "Usual suppliers...",
minimumInputLength: 1,
multiple: true,
id: function(e) {
return e.id + ":" + e.name;
},
ajax: {
url: ROOT + 'Ajax',
dataType: 'json',
type: 'POST',
data: function(term, page) {
return {
call: 'Record->supplierHelper',
q: term,
page_limit: 10
};
},
results: function(data, page) {
return {
results: data.suppliers
};
}
},
formatResult: formatResult,
formatSelection: formatSelection,
initSelection: function(element, callback) {
var data = [];
$(element.val().split(",")).each(function(i) {
var item = this.split(':');
data.push({
id: item[0],
title: item[1]
});
});
//$(element).val('');
callback(data);
}
});
Is there a way for a new tag to be created if the text typed does not exist? Initially I thought this could some how be done by delimiting with spaces, but some items (supplier names) will have spaces in them, so that won't work.
I think when no matches are found the user needs to somehow "create" the tag by pressing a button that could appear in the drop down box, but I have no idea how to do this.
How can I allow users to create new tags that may have spaces in them and still be able to carry on adding more tags, existing or otherwise?
Yes you can do it. There is a example in the documentation. Look at http://ivaynberg.github.io/select2/#events
$("#e11_2").select2({
createSearchChoice: function(term, data) {
if ($(data).filter( function() { return this.text.localeCompare(term)===0;
}).length===0) {
return {id:term, text:term};
}
},
multiple: true,
data: [{id: 0, text: 'story'},{id: 1, text: 'bug'},{id: 2, text: 'task'}]
});
You have to create a function like createSearchChoice, that returns a object with 'id' and 'text'. In other case, if you return undefined the option not will be created.
I'm using jqGrid in a project, and have managed to replace some of the controls on the edit/input modal with a jQuery autocomplete control, but would prefer something like a combobox.
How would it be possible to replicate the functionality, as I'm struggling to get any of the jQuery combobox add-ons working.
My data set is in json format, so it would be cool if I can keep it that way.
I think the jQuery plugin you're looking for is Flexselect which implements the Liquid metal search ranking algorithm to create the desired affect.
This is what I did to turn my autocompletes into comboboxes.
initImpactEdit = function (elem) {
setTimeout(function () {
$(elem).autocomplete({
source: function (request, response) {
$.ajax({
url: '#Url.Action("ImpactOptions")',
dataType: "json",
data: {
filter: request.term
},
success: function (data) {
response($.map(eval(data), function (item) {
return {
label: item.Impact_name,
value: item.Impact_name,
DTI_ID: item.DTI_ID
}
})
);
}
})
}
}
});
$(elem).addClass('customAutoCompleteWidth');
$('<button class="customDropdown"> </button>')
.attr("tabIndex", -1)
.attr("title", "Show All Items")
.insertAfter(elem)
.button({
icons: {
primary: "ui-icon-triangle-1-s"
},
text: false
})
.removeClass("ui-corner-all")
.addClass("ui-corner-right ui-button-icon")
.click(function () {
var widg = $(elem);
if (widg.autocomplete("widget").is(":visible")) {
widg.autocomplete("close");
return;
}
if (widg.val().length == 0) {
// pass empty string as value to search for, displaying all results
widg.autocomplete("search", "*");
} else { widg.autocomplete("search", widg.val()); }
widg.focus();
});
}, 100);
};
{ name: 'Impact', index: 'Impact', editoptions: { dataInit: initImpactEdit } },