Description
I am using a jquery plugin chosen which pretty much does something like this:
This lets me add each option one by one or remove each option one by one. For every option selected, I create a new element with the selected option's value as the id.
Problem
The problem is when I remove an option from the list. For example:
$('#multiple-select').on('change', function(e){
alert($(e.target).val());
});
Will return the correct value if an option is added, however it returns null if we remove an option. I need to be able to get the value of the option being deselected so I can remove it in the other element.
Question
How can I get the deselected option's value to return the actual value instead of null? Or is there another way to bypass this problem?
All I need to be able to do is find the option being deselected and removing it from the other element (knowing that the element's id is built on the option's value).
Update
Remove code as requested:
$('body').on('change', benefs, function(e){
var $nbparts = $(participantNbParts),
$target = $(e.target),
$val = $target.val(),
$name = $target.text();
if($val == null){
//this is because we deleted something thus we need to remove it from $nbparts which is a pitty since we don't know what it was before it got deleted
}else{
//someone was added
$(create_row_expense_nb_parts_participant($name, $val)).appendTo($nbparts).show('slow');
$nbparts.parent().show('fast');
}
});
jQuery chosen provides selected and deselected using which you can identify selected and deselected values respectively, like:
$("#your_element_id").on('change', function (evt, params) {
var selected = params.selected;
var removed = params.deselected; //gives you the deselected value
//assuming your option ids are numbers
if( removed > 0 ) {
console.log( "Value removed is:" + removed );
}
});
From its documentation in the change event description you have
Chosen triggers the standard DOM event whenever a selection is made
(it also sends a selected or deselected parameter that tells you which
option was changed).
This suggests you should observe the arguments received by the event handler at run time to get a hint about (and most likely a reference to) the removed/deselected option.
Related
My question is, using javascript / jquery, "How do you change the value of a dropdown option at a specific index that is NOT the selected index?"
I have a dropdown list of values. User can select an option. I have a method which enables the user to change the value at that selected option. The value gets changed and all is well.
Here is my issue: If the user decides to cancel, or changes to a different value in the list without saving the changes to the database, I want to undo the value change.
I have the index of the changed option.
I have the old value of the changed option.
I have the new value of the changed option.
If the user has selected a different option, I don't want to change the index of the newly selected option. I just want to reset the value of the option the user changed.
I've tried a .each method:
var changedTitle = $('#ddTitle').text();
$("#ddTitle option").each(function() {
if($(this).text() == changedTitle) {
$(this).text(savedTitle);
}
});
I like the idea of looping through each one but I never see execution loop through a second time and the browser never comes back.
I've tried a .filter method:
var changedTitle = $('#ddTitle').text();
$("#ddTitle option").filter(function(index) { return $(this).text() === changedTitle; }).attr('selected', 'selected');
$("#ddTitle option").filter(function() {
return $(this).text() === changedTitle;
}).prop('selected', true); // changes the selected option
I got the above filter code to work but it sets the selected option.
$("#ddTitle option").filter(function() {
return $(this).text() === changedTitle;
}).prop('text', savedTitle); // execution never returns
I tried using the text property on the option but jquery gets very busy and execution never returns.
I've tried finding by the text value, which is silly because I know the index:
$("#ddTitle option[value='" + theText + "']").attr('selected', 'selected');
If these get an option it is the first option (0) or the browser hangs.
Is there a way to change the text value at a specified index programmatically in javascript or using jquery? Nothing I've tried works.
To change the value of the 5th option, do:
$('#yourselect').children('option:eq(4)').html('your text');
Although this may sound dead simple, the matter is complicated by the fact I can only use the change() trigger on the select element. I am using the 'Chosen' jQuery plugin which basically modifies the multi select box on the page.
Whenever a item is selected or unselected, the plugin triggers the change event on the original select element. I am obviously able to get all the unselected items, but I need the one that was just unselected that caused the change event to trigger.
So I have the following function, the bit in the middle is what I need to capture the item that was just unselected. #cho is the id of the original select element.
$("#cho").chosen().change( function() {
// Need code here to capture what item was just unselected, if any...
})
Store value when the user changes the the check box.
var preVal;
$("input[name='g']").on("change",function(e){
if(preVal){
alert(preVal);
}
preVal=$(this).val();
});
Check this http://jsfiddle.net/fcpfm/
1.Use hidden field
2.Hidden field value initially empty.
3.Onchange put the selected value in a hidden field.
4.If onchange is happening again , hidden field value is the previously selected value.
$("#cho").chosen().change( function() {
var hidvalue = $('#hiddenfield').val();
if (hidvalue ) {
//Get the previously selected ids
var prev_ids = $('#hiddenfield').val();
//Then Update currently selected ids
$('#hiddenfield').val('currently selected ids');
} else {
//Update currently selected ids
$('#hiddenfield').val('currently selected ids');
}
})
Try using a variable to store the selected item. Update it each time when item changed. I cant add comment. That is why I am posting it as an answer.
i am trying to bind an event when user selected an item from <select>
not necessary changed from the default.
$(select).change(); only works if the item was changed.
i wonder if there is something that works by selecting one of the options even if its the same default option.
$('#page_body').on('select', '.pop_pin_select', function() {
});
This is what i try so far but it wont work.
There is a way around this; making the option at index 0 the default selected, dynamic and not manually selectable (i.e. disabled) and listen for onchange as normal, except when changing to index 0. Then onchange, set .options[0] to chosen label and value and change selection to it. Here is an example.
Relevant JavaScript from example
document.getElementById('sel')
.addEventListener('change', function () {
if (this.selectedIndex === 0) return;
this.options[0].value = this.value;
this.options[0].textContent = this.options[this.selectedIndex].textContent;
this.selectedIndex = 0;
}, false);
onchange will fire when a user makes the same selection because the index is changing even though the value isn't.
I want to add the text that a user inputs in the text field of a chosen select multiple input as an option, and automatically select it, all of this when the option doesn't exists, if the option exists, then I would like to select it. So far I have manage to do this:
Chosen.prototype.add_text_as_option = function () {
$('#id_select').append(
$('<option>')
.html(this.search_field.val())
.attr('selected', 'selected')
.attr('value', 0)
);
$('#id_select').trigger("liszt:updated");
return false;
};
I call this function whenever the users presses enter while the input field is in focus within the keydown_check function.
I have two problems:
Top priority, when the user presses enter and has typed a substring of an option, the option won't get selected, but the substring text will be added and selected. Not what I want.
For instance: If I have the option "foo", and start typing "fo", chosen will mark the first
option as candidate ("foo"), so if I press enter, it should be selected, but instead, what happens is that "fo" is added as an option and selected, when I actually wanted to select "foo".
If I select "foo" with a click, then everything works fine. The option chosen marks is selected and the substring text is taken as part of the option.
How can I add a non existent option to chosen, without loosing all the original functionality?
How can I access the select multiple field I initilized whith chosen inside the chosen plugin? As you can see in the code above, the id of the select multiple field is hardcoded. I want to do this to be able to refresh the select when the user adds a new option.
The functionality that I'm looking for is very similar to the skills widget of linkedin
You should try out the select2 plugin which is based off of chosen plugin but it works well with adding elements dynamically.
Heres the link: http://ivaynberg.github.com/select2/
Look at the example for auto-tokenization I think that might be what you are looking for.
I needed this today so I wrote something like this:
$(function() {
// form id
$('#newtag').alajax({
// data contains json_encoded array, sent from server
success: function(data) {
// this is missing in alajax plugin
data = jQuery.parseJSON(data);
// create new option for original select
var opt = document.createElement("OPTION");
opt.value = data.id;
opt.text = data.name;
opt.selected = true;
// check if the same value already exists
var el = $('#tags option[value="' + opt.value + '"]');
if( !el.size() ) {
// no? append it and update chosen-select field
$('#tags').append( opt ).trigger("chosen:updated");
} else {
// it does? check if it's already selected
if(!el[0].selected) {
// adding already existent element in selection
el[0].selected = true;
$('#tags').trigger("chosen:updated");
} else {
alert("Already selected and added.");
}
}
}
})
});
"#"newtag is a form, ".alajax" is a plugin that sends form data in async way and returns server's response in JSON format. In the controller I check if a tag exists otherwise I create it. In response I five "jsoned" tag object.
I created a jsfiddle of jquery chosen which takes text and create as option. In earlier version of jquery chosen have facility create option.
create_option: true;
persistent_create_option: true;
skip_no_results: true;
You can use this code:
$('#id_select').chosen({
width: '100%',
create_option: true,
persistent_create_option: true,
skip_no_results: true
});
jsfiddle link: https://jsfiddle.net/n4nrqtek/
just call it keyup_check
keydown_check is called before the pressed letter is initialized
unlike keyup_check
I found a solution multiple select
var str_array = ['css','html'];
$("#id_select").val(str_array).trigger("chosen:updated");
I have a table in which a few columns contains select elements. In the tfoot I have one input element for each row used for filtering the row based on the selected value in the select element.
When loading the table and directly filtering the columns with selects, than it works and the table is filtered.
But when making a change in the select elements, the filter function is not taking any notice that the value has changed.
Checking out the html I can see that the "selected" attribute is still on the option that was selected when loading. Hence, it doesn't get updated when making an actual changed (identified in both FF and Chrome).
But from jQuery, searching for the selected value (.find(":selected")) works. So I figure that I can use that to find the value and then set the selected attribute to whatever was selected. This is how I am trying to do it:
$("select[id^='qu_owner']").live('change', function (e) {
var owner = $(this).val();
console.log(owner);
var ticketid = $(this).attr('id').substr(9);
$($(this) + " option[value=" + owner + "]").attr("selected", "selected"); //Update: this has been removed
});
But the selected attribute is still not updated in the element.
Any clue how to do this? I need the filtering to work and it's looking at the selected attibute. Is it not possible to make this kind of update to the select element?
UPDATE
Ok, based on the comments and answers below I understand there are better ways of doing what I did above. So instead of using $(this).find(":selected").val(); I now use $(this).val();. Also, I did remove the last row since I understand one shouldn't try to set the selected attribute.
And also, I now understand that the code where I have the actual problem is the filter function. This is for DataTables so it's a plugin but this is the significant part:
aData[i] is the actual table cell. Hence, it's just text but in this case it's the text for my select element. I think below is heading in the right direction, but still not working (check comments next to console.log-rows):
function( oSettings, aData, iDataIndex ) {
var ret = true;
//Loop through all input fields i tfoot that has class 'sl_filter' attached
$('tfoot .sl_filter').each(function(i, obj){
//$(this) can be used. Get the index of this colum.
var i = $("tfoot input").index($(this));
//Create regexp to math
var r = new RegExp($(this).val(), "i");
//Get the selected option from the column
console.log($(aData[i]).attr('id')); //Properly prints the ID
console.log($(aData[i] + " option:selected").text()); //Prints all options, not only the selected on
console.log($(aData[i] + " option:selected").val()); //Prints the value of the id that was selected when data was loaded, even if a new option has been chosen
console.log($(aData[i]).val()); //Prints the value of the id that was selected when data was loaded, even if a new option has been chosen
var str = $(aData[i] + " option:selected").text();
/*Test to see if there is a match or if the input value is the default
(the initial value of input before it has any fokus/text) */
if(r.test(str) || $(this).val()=="Search"){
//Return true only exits this function
return true;
}else{
/*Return false returns both function an .each. Retain 'false' in a variable scoped
to be reached outside the .each */
ret = false;
return false;
}
});
//Return true or false
return ret;
}
It is the text for the selected element I need to get hold of. That's what should be filtered upon. How can I do that?
Update
To narrow it down, I have created a jsfiddle with what's necessary. It's all about how to extract the text from the selected option: jsfiddle
aData[i] = the table cell. In jsfiddle, i use "sel" as variable for the content of the cell. The text for sel is copied form aData[i].
There's no need to change the attribute of the <option> - that's supposed to contain the original state of the element as it was downloaded from the server.
Your filter should be checking the selected property of the chosen option, e.g.:
.filter(function() {
return this.selected; // check the boolean property
})
This is also how the :selected pseudo-selector works - it checks the current value of the property, not the attribute.
Note that in the change handler for a <select> element, you can just use this.value to get the currently selected value.
$('select').on('change', function() {
// current value
var value = this.value;
// text of the currently selected option.
var text = this.options[this.selectedIndex].text;
}