I have below form, where each .form-row is dynamically added using jQuery when user clicks on Add New button.
My html form (simplified)
<div id="total_sum">
<!-- here will show up total amount, which is sum of unit[] * price[] - discount[] of all below form-rows -->
</div>
<div id="total_discount">
<!-- here will show up total discount amount, which is sum of discount[] of all below form-rows -->
</div>
<div id="total_net">
<!-- here will show up net amount, which is total_sum - total_discount -->
</div>
<form id="form" method="POST" action="">
<div class="form-row">
<select name="item[]">
<option value="item-id-1">Item 1</option>
<option value="item-id-2">Item 2</option>
<option value="item-id-3">Item 3</option>
</select>
<input type="number" class="unit" value="1" name="unit[]" />
<input type="number" class="price" name="price[]" />
<input type="number" class="discount" name="discount[]" />
<input type="number" class=name="sum[]" />
</div>
<div class="form-row">
<select name="item[]">
<option value="item-id-1">Item 1</option>
<option value="item-id-2">Item 2</option>
<option value="item-id-3">Item 3</option>
</select>
<input type="number" class="unit" value="1" name="unit[]" />
<input type="number" class="price" name="price[]" />
<input type="number" class="discount" name="discount[]" />
<input type="number" class="sum" name="sum[]" />
</div>
<!-- and users can dynamically add as many form-rows as they want -->
<div class="form-row">
<select name="item[]">
<option value="item-id-1">Item 1</option>
<option value="item-id-2">Item 2</option>
<option value="item-id-3">Item 3</option>
</select>
<input type="number" class="unit" value="1" name="unit[]" />
<input type="number" class="price" name="price[]" />
<input type="number" class="discount" name="discount[]" />
<input type="number" class="sum" name="sum[]" />
</div>
</form>
And what I am trying to achieve is two-folded:
calculate the sum of each line (.form-row) and display the sum in each line (in sum[] field)
calculate the sum of all sums and discounts of all lines (all .form-rows) and display them in #total_sum, #total_discount, and #total_net.
I believe I need something that gets all .form-rows, which is triggered whenever there is a change in the form (or every 1 second, perhaps?), and loop through them to calculate respective sum, and calculate the total of sums and discounts when looping is over. I can do this if it's PHP, but I am quite new to jQuery or Javascript so I have no idea where to look into first.
[Adddd]
One thing I did not mention in above explanation is that unit[] has default value of 1 and price[] is at first automatically appended using AJAX, and then users can change the value.
My AJAX to automatically retrieve price when user selects an item.
<script>
jQuery(document).ready(function($) {
/* Get Item Price and Item Currency */
$('#form').on('change', '.item_id', function(){
var this$ = $(this);
var $item_id = this$.val();
var ajaxurl = '<?php echo admin_url('admin-ajax.php'); ?>';
// call ajax for item price (returns 0 if item has no price)
$.ajax({
url: ajaxurl,
data:' action=get_item_price_by_id&item_id='+$item_id,
type:'GET',
success:function(results) {
this$.parent().parent().find('.price').empty();
this$.parent().parent().find('.price').val(results);
}
});
});
});
</script>
Thanks to the advice from Manish Jangir Blogadditic, I came to have below code:
<script>
jQuery(document).ready(function($) {
// Calculate sub-sums on any form changes
$("#form").change(function() {
var sum = 0;
$('.form-row').each(function() {
sum = Number( $(this).find('unit').val()) * Number( $(this).find('price').val() );
alert( sum );
});
});
});
</script>
However, it works when the form is manually changed, but doesn't work when price is automatically appended by ajax.
Any other suggestions?
If your button #form comes with the last added dynamic element then you can try this out because .change or .on don't work with dynamically appended html elements. jQuery has given a $(document).on event to do that.
jQuery(document).ready(function($) {
// Calculate sub-sums on any form changes
$(document).on('click','#form',function() {
var sum = 0;
$('.form-row').each(function() {
sum += Number( $(this).find('.unit').val()) * Number( $(this).find('.price').val() );
alert( sum );
});
});
});
Value changed by Javascript will not trigger onchange event. And this rule applied on JQuery's change function too. So you may need to manually trigger onchange event after the updating. With Jquery you may use .trigger(), check here: http://api.jquery.com/trigger/
Try this code it will resolve your issue.
jQuery(document).ready(function() {
// Calculate sub-sums on any form changes
$("#form").on('change',function() {
var sum = 0;
$('.form-row').each(function() {
sum += parseInt($(this).find('.unit').val()) + parseInt($(this).find('.price').val());
});
});
});
You have to create a delegated event.
jQuery(document).ready(function() {
// Calculate sub-sums on any form changes
$("#form").on('change','.price, .unit',function() {
var sum = 0;
$('.form-row').each(function() {
sum = Number( $(this).find('.unit').val()) * Number( $(this).find('.price').val() );
alert( sum );
});
});
});
Related
This question already has answers here:
Bind events on dynamic created elements inserted by AJAX (check box)
(2 answers)
Closed 9 years ago.
I am having a problem with dynamic generated checkbox. I have tried like this :
<select name="model" id="model" class="" aria-invalid="false">
<option value="1">iPhone 5</option>
<option value="2">Iphone 4S</option>
<option value="3">Iphone 4</option>
</select>
Based on above selected value these checkbox will generated through ajax.Here are the element generated through ajax:
<p><input type="checkbox" id="screenguard" name="screenguard" value="20" />Cover</p>
<p><input type="checkbox" id="Charger" name="Charger" value="30" />Charger</p>
<p><input type="checkbox" id="hdphdm" name="hdphdm" value="10" />Headphone</p>
<p>
Calculated Price: <input type="text" name="price" id="price" />
</p>
And based on selection made of checkboxes I need to calculate the value in to another input box(price) . Here is my Jquery function :
$(document).ready(function () {
var $inputs = $('input[type="checkbox"]')
$inputs.on('change', function () {
var sum = 0;
$inputs.each(function() {
// iterate and add it to sum only if checked
if(this.checked)
sum += parseInt(this.value);
});
$("#price").val(sum);
});
});
But I don't know why it's not working. Please give me any suggestion, what I am doing wrong.
You need to use event delegation like this -
$(document.body).on('change','input[type="checkbox"]', function () {
Every time you click a checkbox 'sum' is reset back to zero. Move it outside of the 'change' event.
I have a form with 2 dropdowns, 'Type' and 'Level', eg
Type
-----
Hotel
Restaurant
Casino
Level
-----
1
2
3
And a submit button which shows the price based on whichever options are selected in the dropdown. The price is calculated by some basic maths on the fly.
How can I do this using jquery?
Is it using onchange() or something?
$("#button_id_here").val("$your_amount_here");
If you want it to update automatically, bind it to the change event in the select/dropdowns
$("#select_id_here").change(function(){
//"basic maths"
$("#button_id_here").val("$your_amount_here");
});
You want more help, we would need to see code.
HTML:
<form>
<fieldset>
<p>
<label for="selectType">Type:</label>
<select id="selectType" name="type">
<option value="Hotel" data-cost="40">Hotel</option>
<option value="Restaurant" data-cost="80">Restaurant</option>
<option value="Casino" data-cost="35">Casino</option>
</select>
</p>
<p>
<label for="selectLevel">Level:</label>
<select id="selectLevel" name="level">
<option value="1" data-cost="0">1</option>
<option value="2" data-cost="15">2</option>
<option value="3" data-cost="30">3</option>
</select>
</p>
<p>
Total Cost: $<span id="cost">0</span>
</p>
<p><input type="submit" value="Go!"></p>
</fieldset>
</form>
jQuery:
$(function() {
$("#selectType, #selectLevel").change(function() {
var type = $("#selectType"),
level = $("#selectLevel"),
cost = $("#cost"),
typeCost = type.find(":selected").data('cost'),
levelCost = level.find(":selected").data('cost'),
total = typeCost + levelCost;
cost.html(total);
}).change(); // invoke the .change() trigger
});
See it in action here
You might want to also set something like "data-multiplier" for the level... whereas level 2 may have a 1.5x multiplier, and level 3 may have a 2x multiplier. You'd have to adjust the jQuery accordingly as well (total = typeCost * levelCostMultiplier, for example).
You can check if a select list has changed via jQuery's change() function.
Here's a way to do it:
HTML:
Type
<select name="type" id="type">
<option value="hotel" selected>Hotel</option>
<option value="restaurant">Restaurant</option>
<option value="casino">Casino</option>
</select>Level
<select name="level" id="level">
<option value="1" selected>1</option>
<option value="2">2</option>
<option value="3">3</option>
</select>
<div id="result"></div>
jQuery:
var result = 1;
$("#type").change(function () {
var val = $(this).val();
$("#result").html("Type is " + val + ", level is " + $("#level").val());
});
$("#level").change(function () {
var val = $(this).val();
// Some basic math
result = parseInt(val) * 5;
$("#result").html("Type is " + $("#type").val() + ", level is " + val + ", result: " + result);
});
And the relevant jsfiddle:
http://jsfiddle.net/y2s4v/1/
I need to show the item_id when I click one of the item_name list in the dropdown. And when I click submit, the item_name and item_id got by $_POST. Can javascript use to do that?
<?php
$brg="SELECT item_id, item_name FROM tblItem";
$b=mysql_query($brg);
?>
<td align="center">
<select name="item_name">
<?php while($br=mysql_fetch_array($b)){ ?>
<option value=<?echo $br[0].'_'.$br[1]?> selected>
<?php echo $br[1]; ?>
</option>
<?php } ?>
</select>
</td>
Jup, that's possible with Javascript.
Your HTML:
<select name="item_name">
<option value="1_Cheese">Cheese</option>
<option value="2_Cars">Cars</option>
<option value="3_Planes">Planes</option>
</select>
<input type="button" onclick="alert(getSelectedValue())" value="Get Select Id" />
And your Javascript, to access the ID from the options value:
function getSelectedValue()
{
var sel = document.getElementsByName('item_name')[0];
return sel.options[sel.selectedIndex].value.split("_")[0];
}
See this fiddle: http://jsfiddle.net/acz6Q/
It would be a little easier with jQuery (also appended an event handler):
$(document).ready(function()
{
$("select[name=item_name]").on("change", function()
{
alert("new item id = " + $(this).val().split("_")[0]);
});
});
And here is the jQuery version fiddle: http://jsfiddle.net/acz6Q/1/
Hope this helps!
Try this:
<form action="" method="post">
<input type="hidden" id="item_id" name="item_id" />
<input type="hidden" id="item_name" name="item_name" />
<select id="my_select" name="my_select">
<option value="item_id_1">item_name_1</option>
<option value="item_id_2">item_name_2</option>
<option value="item_id_3">item_name_3</option>
</select>
</form>
<script type="text/javascript">
$(document).ready(function() {
$("#my_select").change(function() {
$("#item_id").val($("#my_select").val());
$("#item_name").val($("#my_select option:selected").text());
});
});
</script>
Note that you need to include the jQuery library first. Also you can see how it works from here jsfiddle.net/2FsNP/3. And with this method you don't need to combine between value and text of the option tag with the underscore.
i have a dropdown where there is a value of pixels and below is a div with some data and
the div is of some width and height but what i need to do is when i select any value lets
suppose i selct 350px then the size of the div should automatically adjust accordingly. i
dont have any idea how to do that refer me any link so that i could get help from there.
i am serching for it or any kind of help on google for the last one hour.
here is the html
<td>
<select name="sizi_pixel" id="drp">
<option value="1">100 Pixels</option>
<option value="2">200 Pixels</option>
<option value="3">350 Pixels</option>
<option value="4">450 Pixels</option>
<option value="5">600 Pixels</option>
</select>
</td>
and here is the div i want to resize automatically
<div style=" border-width:3px;border-style:solid;border-color:#ff9900; height:400px; width:300px">
<input class="color" value="999">
<input class="color" value="999">
<input class="color" value="999">
</div>
any help will be appreciated
This javascript should do the trick!
You need to attach an event listener to your select input, also change the options to represent the value in the box. And give your div an id, I gave it the id 'myDiv'.
you can also see it working here: http://jsfiddle.net/6avqc/1/
document.getElementById('drp').addEventListener('change', changeSize);
function changeSize() {
var myDiv = document.getElementById('myDiv');
var selectbox = document.getElementById('drp');
var index = selectbox.selectedIndex;
var value = selectbox[index].value;
myDiv.style.width = value + 'px';
}
Give your div an id and add an event listener for the change Event of your list view. Everytime the event is raised, you can change the size of the list
<script>
$(function() {
$("#drp").change(function() {
$("#rect").width($(this).val() + "px");
});
});
</script>
you have to include jquery in your page and modify the vals of your list to match the widths
Here is an working example if you have additional questions feel fre to ask:
Jsfiddle DEMO: http://jsfiddle.net/kPFry/
<html>
<head>
<style>
input {
position: relative;
width: 90%;
}
</style>
<script>
function chng_div(src_id,div_id){
var src_obj = document.getElementById(src_id);
var div2chg = document.getElementById(div_id);
div2chg.style.width = src_obj.value+"px";
}
</script>
</head>
<body>
<select name="sizi_pixel" id="drp" onchange="chng_div('drp','div_to_chng');">
<option value="100">100 Pixels</option>
<option value="200">200 Pixels</option>
<option value="350">350 Pixels</option>
<option value="450">450 Pixels</option>
<option value="500">600 Pixels</option>
</select>
<div style="border-width:3px;border-style:solid;border-color:#ff9900; height:400px; width:300px" id="div_to_chng">
<input class="color" value="999">
<input class="color" value="999">
<input class="color" value="999">
</div>
</body>
</html>
this is just an example, please do not use inline CSS styles ever long term it would cost you too much.
I am trying to show and hide a few form fields depending on the value of one of my select fields. I am looking to use arrays to hold what should be shown and what should not be shown for each select value, to save me from a massive switch statement, but cannot figure out how to do it.
I am using PHP and jQuery. Any help would be great.
Try something like this:
<select id="viewSelector">
<option value="0">-- Select a View --</option>
<option value="view1">view1</option>
<option value="view2">view2</option>
<option value="view3">view3</option>
</select>
<div id="view1">
<!-- content -->
</div>
<div id="view2a">
<!-- content -->
</div>
<div id="view2b">
<!-- content -->
</div>
<div id="view3">
<!-- content -->
</div>
then in the jQuery:
$(document).ready(function() {
$.viewMap = {
'0' : $([]),
'view1' : $('#view1'),
'view2' : $('#view2a, #view2b'),
'view3' : $('#view3')
};
$('#viewSelector').change(function() {
// hide all
$.each($.viewMap, function() { this.hide(); });
// show current
$.viewMap[$(this).val()].show();
});
});
There are a few different ways you could do this. The simplest is to have a few separate fieldsets, each one containing a single group of fields. Then, in jQuery, dependent on the select-menu's value you can show/hide these fieldsets, e.g.
<fieldset id="f1">
<input name="something1" />
<input name="something2" />
<input name="something3" />
</fieldset>
<fieldset id="f2">
<input name="something4" />
<input name="something5" />
<input name="something6" />
</fieldset>
<select name="fieldset-choice">
<option value="f1">Fieldset 1</option>
<option value="f2">Fieldset 2</option>
</select>
<script type="text/javascript">
jQuery('select[name=fieldset-choice]').change(function(){
var fieldsetName = $(this).val();
$('fieldset').hide().filter('#' + fieldsetName).show();
});
// We need to hide all fieldsets except the first:
$('fieldset').hide().filter('#f1').show();
</script>
Note: For the above technique to be entirely unobtrusive you might want to dynamically build the select-menu with the names of all the different fieldsets.
Alternatively you can prefix each fields name with a meaningful prefix, and then hide/show according to that attribute:
<input name="group1-name1" />
<input name="group1-name2" />
<input name="group2-name3" />
<input name="group2-name4" />
<input name="group2-name5" />
<select name="field-choice">
<option value="group1">Group 1</option>
<option value="group2">Group 2</option>
</select>
<script type="text/javascript">
jQuery('select[name=field-choice]').change(function(){
var groupName = $(this).val();
$('input').hide().filter('[name^=' + groupName + ']').show();
});
// We need to hide all fields except those of the first group:
$('input').hide().filter('[name^=group1]').show();
</script>
To fire up the code on load, just add .change(). As shown below...
$(document).ready(function() {
$.viewMap = {
'0' : $([]),
'view1' : $('#view1'),
'view2' : $('#view2a, #view2b'),
'view3' : $('#view3')
};
$('#viewSelector').change(function() {
// hide all
$.each($.viewMap, function() { this.hide(); });
// show current
$.viewMap[$(this).val()].show();
}).change();
});
My 2 cents :
I needed to show/hide fields depending on many previous select value (not only one).
So I add a parent attribute to div fields like this :
<div id="view" parent="none">
<select class=selector id="view">
<option value="0"> -- Make a choice --</option>
<option value="s1">sub 1</option>
<option value="s2">sub 2</option>
<option value="s3">sub 3</option>
</select>
</div>
<!-- you need to define the parent value with the value of parent div id -->
<div id="s1" parent="view">
<!-- if you want to have a selector be sure it has the same id as the div -->
<select class=selector id="s1">
<option value="0">-- Make a choice --</option>
<option value="s1_sub1">sub 1 of s1</option>
<option value="s1_sub2">sub 2 of s1</option>
<option value="s1_sub3">sub 3 of s1</option>
</select>
</div>
<!-- Make the same thing for s2 and s3
Define div s2 here
Define div s3 here
-->
<!-- and finally if that's your final step you put what you want in the div -->
<div id="s1_sub1" parent="s1">
You are inside s1 sub1
</div>
Now the jquery code :
$(document).ready(function() {
$('select[class=selector]').change(function() {
//next div to show
var selectorActive = $(this).val();
//div where you are
var parentValue = $(this).attr("id");
//show active div and hide others
$('div').hide().filter('#' + selectorActive).show();
while (parentValue!="none") {
//then show parents of active div
$('div[id=' + parentValue + ']').show();
//return the parent of div until "none"
parentValue = $('div[id=' + parentValue + ']').attr("parent");
}
});
// print only the first div at start
$('div').hide().filter("#view").show();
});
That's works like a charm and you don't need to define maps
I hope this will help
#Martin Try this
`$('#viewSelector').trigger('change');`
Here is a very simple example:
The purpose is to show A SIMPLE EXAMPLE of how to use an array of values to show/hide fields depending upon the value of a select.
In this demo, I could have used the classNames to show/hide the group of fields all-at-once -- but that's not the purpose of the example -- so the classNames were used only for CSS.
Because the demo uses IDs (with two arrays of these IDs) for the demo, it doesn't matter whether the fields to be hidden are input fields, divs, imgs or what-have-you. The ID identifies whatever-it-is-to-be-hid.
var aPeople = ['bob','sam','ted'];
var aTransport = ['car','bike','truck'];
$('#mySel').change(function(){
$('.alldiv').hide(); //Hide them all to start...
let sel = $(this).val(); //Get selected option value
if ( sel=='ppl' ){
for (let i=0; i<aPeople.length;i++){
$('#' + aPeople[i]).show();
}
}else if ( sel=='tpt' ){
for (let i=0; i<aTransport.length;i++){
$('#' + aTransport[i]).show();
}
}else{
//Choose selected
$('.alldiv').show();
}
});
.alldiv{width:30vw;height:10vh;padding:2vh 2vw;text-align:center;}
.ppl{background:palegreen;}
.tpt{background:wheat;}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.4/jquery.min.js"></script>
<select id="mySel">
<option value="">Choose:</option>
<option value="ppl">People</option>
<option value="tpt">Vehicles</option>
</select>
<div id="bob" class="alldiv ppl">People: Bob</div>
<div id="car" class="alldiv tpt">Vehicle: Car</div>
<div id="truck" class="alldiv tpt">Vehicle: Truck</div>
<div id="sam" class="alldiv ppl">People: Sam</div>
<div id="ted" class="alldiv ppl">People: Ted</div>
<div id="bike" class="alldiv tpt">Vehicle: Bike</div>