I have a dropdown select list on my page of class="TypeFilter".
I have a jQuery event that fires when a value in that list is selected.
$(".TypeFilter").change(function()
{
// Extract value from TypeFilter and update page accordingly
));
I now have to add another list to the page, and I want to implement functionality which will prevent the .change(function() from running unless both are selected.
In both lists the first option in the list is some text instructing the user to select one of the items, so I was thinking of just writing some logic to test that both lists have a selected index greater than 0.
I think this is a touch unclean though, especially considering that other pages that have a TypeFilter use the same logic.
Is there any nifty functionality in jQuery that can do this?
edit I should specify that the user needs to be able to update the page by selecting either dropdown, so I can't put the onchange on the second element and test that the first element has a selected value, as suggested in one of the answers
If you bind the same event to all dropdowns, you can get a collection of all the dropdowns and check that all of them are selected. Example:
$('.Dropdown').change(function(){
var elements = $('.Dropdown');
if (
elements.filter(function(){
return this.selectedIndex > 0;
}).length == elements.length
) {
// all dropdowns are selected
}
});
As you partly mention, put the onchange on the second element and test that the first element has a selected value before you fire off any logic.
Use bind instead, and as the eventdata, send a function that checks that either that both are selected or that the other is selected. Untested code:
function checker() {
// test your conditions
}
$(".TypeFilter").bind('change', {test: checker}, function(event)
{
if (event.data.test && event.data.test()) {
// Extract value from TypeFilter and update page accordingly
}
));
This way the other pages that use the same function will not notice any changes.
Related
I have some issue understanding the jQuery().change() behavior.
The HTML is basically a lot of input elements - checkboxes ( each with ID of id^='o99-post-visible-XXX' - and they are pure CSS images as Checkboxes, but this is irrelevant ) and I have another checkbox ("#o99-check-all") to "check all" and a text input field ('#o99-post-visible-ids') that receives the IDs of the selected boxes.
The jQuery code is as follows:
jQuery(document).ready(function() {
jQuery("#o99-check-all").change(function () {
jQuery("input:checkbox[id^='o99-post-visible-']").prop('checked', jQuery(this).prop("checked")).trigger('change');
});
var checkboxes = jQuery("input.o99-cbvu-posts-checkbox:checkbox");
checkboxes.on('change', function() {
// get IDS from all selected checkboxes and make a comma separated string
var ids = checkboxes.filter(':checked').map(function() {
return this.value;
}).get().join(',');
// put IDS inside a text input field
jQuery('#o99-post-visible-ids').val(ids);
// console.log(ids);
});
});
Now, more or less everything works now, but that is not the issue.
at first , the first chunk of code was:
jQuery("#o99-check-all").change(function () {
// without .trigger('change') chained
jQuery("input:checkbox[id^='o99-post-visible-']").prop('checked', jQuery(this).prop("checked"));
});
and it did not work ( why?? ) - meaning the boxes were selected as expected but the '#o99-post-visible-ids' input field was not receiving the IDs - until I chained a .trigger('change') event - when suddenly it works well.
my confusion is with the following ( which perhaps for my little understanding of jQuery internal works is counter-intuitive )
after chain adding .trigger('change') - isn't it somehow an endless loop where a chain() event is trigger inside a listener of change() ? and if not why?
Why is the code functioning now and did not function correctly before? because again, for my understanding, there was a change, even if not triggered by direct user click. Why would I need to trigger it manually?
I'm not sure I understand what you mean. What is happening now, is that whenever you change the all checkbox, the other checkboxes will be checked/unchecked the same as all, and then the change event is triggered.
Because you added a listener for change, that function will then fire. I.e. this function will run:
function() {
// get IDS from all selected checkboxes and make a comma separated string
var ids = checkboxes.filter(':checked').map(function() {
return this.value;
}).get().join(',');
// put IDS inside a text input field
jQuery('#o99-post-visible-ids').val(ids);
// console.log(ids);
}
Without your .trigger("change") (or .change() in short), you only change a property of the inputs. So the object changes, indeed, but that does not mean the change event is triggered. It does sound counter-intuitive, but events are only triggered by user actions or if you call the event explicitly - in no other way do events get triggered.
its because you have written jQuery('#o99-post-visible-ids').val(ids); inside a function which happens only when the change event done on the inputs, assigning prop directly through .prop does not trigger the change event and so the result handler wont run
Now if I understand you correctly...
...because you're giving every check box the same ID? If you wish to apply it to more than a single element, it is best practice to use a class selector instead.
jQuery(".o99-check-all").change(function () {
// without .trigger('change') chained
jQuery(".o99-check-all").prop('checked', jQuery(this).prop("checked"));
});
See link
https://api.jquery.com/change/
please I have a drop down list like
creation
creation from scratch
creation without data
creation pay
modification
modification/specific
modification/clean
and this script
function checkTicketType(tipo) {
console.log("Tipo cambia: "+tipo);
if (tipo.indexOf('Creation')>-1) {
$('#itemId').parent().show(500);
}
else if (tipo.indexOf('Modification')>-1) {
$('#itemId').parent().hide(500);
}
}
When the creation status are selected the itemId box appear, desappear when the modifications are selected.
My problem I want to use the itemId (it can appear only if the status "modification/specific" is selected no more).
Thank you in advance.
Attach change event to select dropdown. Check for selected text on change event.
If it contains modification hide the itemId box (assuming its text input) else if it contains creation show it.
//Change event for dropdown with id ddForEg
$("#ddForEg").change(function(){
if($("#ddForEg option:selected").text().includes('modification'))
{
alert($("#ddForEg option:selected").text());
$('#itemId').hide();
alert($("#ddForEg").val()); //Another way to see value selected. If you assign value to options. No string operations required in that case.
}
else if($("#ddForEg option:selected").text().includes('creation'))
{
$('#itemId').show();
}
})
Fiddle: https://jsfiddle.net/mwoavoqd/
I have attached a JS Fiddle link here:
http://jsfiddle.net/p0b4j5o8/18/
If you check the fiddle link, you will see that I have written JavaScript/jQuery code (a function named add_mitigator()) in the HTML section.
When I used to write the code in the JavaScript section, Firebug used to trigger an error stating function add_mitigator() isn't defined.
But when I wrote the same in the HTML section instead, it runs with no problem. I am not much accustomed with JS Fiddle. How can I write a function in function_name() format in the fiddle?
In my JS Fiddle, there is a dropdown (chosen multiple) with options 1 to 10. When I click on the add_mitigator link, it creates/appends a new chosen dropdown.
Suppose I have three dropdowns, then if I select 2 from dropdown 1, then the other dropdowns will have 2 removed from their options. When I will unselect the 2 from the first dropdown, then 2 will again be available in the other two dropdowns. This should act vice-versa. When 2 is selected from any dropdown, then it is unavailable for all other dropdowns.
How can I achieve this?
By calling the function below on the select box change event the options will be disabled/enabled as per your requirements.
function disableSelectedValues() {
var cssOptions = [];
$(".input_field.criteria_countries option").removeAttr("disabled");
$.each($(".input_field.criteria_countries"), function(index, select) {
cssOptions = [];
var values = $(select).val();
if (values) {
for (var i = 0; i < values.length; i++) {
cssOptions.push("option[value=" + values[i] + "]");
}
}
console.log("test");
if (cssOptions.length) {
// disable all options with the selected values
$(".input_field.criteria_countries "
+ cssOptions.join(",.input_field.criteria_countries ")).attr("disabled", true);
// enable all options with the selected values for the current select
$(select).find(cssOptions.join()).removeAttr("disabled");
}
});
}
With .chosen you can listen to onchange events with .chosen().change();.
In the .chosen().change() event you then need to tell all of the select boxes to update once a value has changed. By using .trigger("chosen:updated"); on the select box selectors whenever a change event is fired, the select boxes will update.
NOTE that you will need to call the disableSelectedValues() function whenever you add a select box to have its options disabled on creation.
http://jsfiddle.net/p0b4j5o8/22/
I have a table with a button that adds a row to the bottom by cloning the last row. Each row contains a <select> with a different name (0-9), all <select> objects have the .variable_priority class. When pressing the button, the row gets copied successfully and I manage to change the name correctly (10, 11, 12, etc.), and the row gets the same class since it is a perfect copy.
However, when I execute the following function, I encounter problems with cloned table rows:
$('.variable_priority').change(function() {
var selections = new Array();
$(".variable_priority").each(function() {
selections.push($(this).find('option:selected').val());
});
// Iterating on Options of Select
$('.variable_priority').children('option').each(function() {
$(this).removeAttr('disabled');
if($.inArray($(this).val(), selections) !== -1){
if($(this).val() != 0){
if($(this).is(':selected')){
// nothing
} else {
$(this).attr('disabled', true);
}
}
}
});
});
The function should run each time I change the selected option of a <select>, though it only runs with the 10 original ones. This function is not executed when I change the option in a cloned row. However, if I change the value in one of the originals, the function runs and it also adds the values from the cloned rows to the selections array.
So for some reason, the code recognizes that the clones have the same class, but it doesn't run when changing their values.
EDIT: short description of the code above; if I change the selected value of a <select>,the function will add all selected options to an array and disable every selected option in the selects, except in the box where the value itself is selected (if I select '2' in the first box, '2' gets disabled in all other boxes).
Because your select element is dynamic (It is added to the DOM after the initial page load, or to be specific; after the initial event handler attachment) you will need to delegate your change event handler:
$(document).on('change', '.variable_priority', function() {
});
Rather than use document though, you'll want to attach the event handler to the closest static element to .variable_priority.
JSFiddle
I think the code isn't executed on the new clones.
This script is loaded on start. It has to do it over for each new children.. Maybe after adding a new, run this script specific for that new one.
I have a select option box that is dynamically populated, so if I change the select some other boxes are filled, and I can delete them too.
Which also deletes the option from the select box, this works fine, but when I delete the options and I have just one left in the box, there seem to be no way to fire the option.
$("#email_name").on("change", function(){
var componentkeys = myDailyemail.getKeys($("#Component").val());
$.each(componentkeys, function(kIndex, kItem) {
$("#key").append($("<option/>").val(kItem).text(kItem.toUpperCase()));
});
});
You can automatically trigger a change event after you populated the select element, making it as if the user already selected the first option.
$("#email_name").on("change", function(){
var componentkeys = myDailyemail.getKeys($("#Component").val());
$.each(componentkeys, function(kIndex, kItem) {
$("#key").append($("<option/>").val(kItem).text(kItem.toUpperCase()));
});
$("#key").trigger("change"); // trigger key
}).trigger("change"); // trigger email_name
I wasn't sure what you wanted to trigger so I entered both possibilities.
You can use .trigger() to fire events manually.
Insert following, where needed.
$("#email_name").trigger('change');