So I have a HTML form which has two dropdown menus and a button. One dropdown menu has 'package type' which consists of 'Gold', 'Silver' and 'Bronze'. The second dropdown menu has 'months' with 12 options (for up to 12 months) and then a calculate button.
Now, this is the bit I hope I can explain well...
If you select 'Silver', and '1 month', it will cost £150.00.
If you select 'Silver', and '2 months', it will cost £225.00.
If you select 'Silver', and '3 months', it will cost £300.00.
And so on (up to 12 months). So the logic for the above is £150.00 for the first month, and then £75 for additional months.
But if you decide you want to have a 'Gold' package, it will be as follows:
If you select 'Gold', and '1 month', it will cost £199.00.
If you select 'Gold', and '2 months', it will cost £298.50.
If you select 'Gold', and '3 months', it will cost £398.00.
And so on (up to 12 months). So the logic for the above is £199.99 for the first month, and then £99.50 for additional months.
And similar for 'Bronze' too, except 1 month is £75.00, 2 months is £112.50 (logic is £75.00 for first month, and £37.50 for additional months).
I hope this makes sense? Below is the HTML for the form, which I know does not work, but this is just to try and explain...
<form name="costcalculator">
<div class="package-type">
<select name="packageType" id="packageType">
<option value="199.00" label="Gold">Gold</option>
<option value="150.00" label="Silver">Silver</option>
<option value="75.00" label="Bronze">Bronze</option>
</select>
</div>
<div class="months">
<select name="months" id="months-bronze">
<option value="£75.00" label="1 month">1 month Bronze</option>
<option value="£112.50" label="2 months">2 months Bronze</option>
</select>
</div>
<div class="months">
<select name="months" id="months-silver">
<option value="£150.00" label="1 month">1 month Silver</option>
<option value="£225.00" label="2 months">2 months Silver</option>
</select>
</div>
<div class="months">
<select name="months" id="months-gold">
<option value="£199.00" label="1 month">1 month Gold</option>
<option value="£298.50" label="2 months">2 months Gold</option>
</select>
</div>
<button type="button" onclick="calculatePrice();showDiv();">Calculate</button>
</form>
What I currently have (that works), is the following, but it doesn't do what I need it to do, this just has the cost hardcoded in, so regardless of the package type, the cost will be the same (except for the initial cost being different for each package):
<form name="costcalculator">
<div class="package-type">
<select name="packageType" id="packageType">
<option value="199.00" label="Gold">Gold</option>
<option value="150.00" label="Silver">Silver</option>
<option value="75.00" label="Bronze">Bronze</option>
</select>
</div>
<div class="months">
<select name="months" id="months">
<option value="100.00" label="1 month">1 month</option>
<option value="200.75" label="2 months">2 months</option>
<option value="275.25" label="3 months">3 months</option>
<option value="349.00" label="4 months">4 months</option>
<option value="369.99" label="5 months">5 months</option>
<option value="450.00" label="6 months">6 months</option>
</select>
</div>
<button type="button" onclick="calculatePrice();showDiv();">Calculate</button>
</form>
And the JavaScript as follows:
function calculatePrice(costcalculator){
var elt = document.getElementById("packageType");
var package = elt.options[elt.selectedIndex].value;
var elt = document.getElementById("months");
var months = elt.options[elt.selectedIndex].value;
package = parseFloat(package);
months = parseFloat(months);
var total = package+months;
document.getElementById("TotalPrice").value=total;
}
So I thought I was nearly there with the working code above, but the more I get into it, the more I realise it's way off.
It just needs a way that when the user selects the package type in the first dropdown menu, then the second dropdown menu containing the months will (behind the scenes) have populated the new costs immediately before the user selects number of months, and then if the user then decides to select a different package to the last one, the second dropdown menu will refresh again but with the different costs in the background.
Here's a simple solution using a simple data structure as per the comment from 04FS. The data structure has the package name as the key, for easy lookup. It has the base price (for the first month) and then the price for additional months, so the total price can be easily calculated.
HTML markup:
<form name="costcalculator">
<div class="package-type">
<select name="packageType" id="packageType" onchange="setMonths(this.value)">
<option value="gold">Gold</option>
<option value="silver">Silver</option>
<option value="bronze">Bronze</option>
</select>
</div>
<div class="months">
<select name="months" id="months">
<option value="1">1 month</option>
<option value="2">2 months</option>
<option value="3">3 months</option>
<option value="4">4 months</option>
<option value="5">5 months</option>
<option value="6">6 months</option>
<option value="7">7 months</option>
<option value="8">8 months</option>
<option value="9">9 months</option>
<option value="10">10 months</option>
<option value="11">11 months</option>
<option value="12">12 months</option>
</select>
</div>
<button type="button" onclick="calculatePrice()">Calculate</button>
<div id="price"></div>
</form>
Javascript code:
var costs = {
'gold': {'basePrice': 199.99, 'pricePerMonth' : 99.5, 'maxMonths': 12},
'silver': {'basePrice': 150, 'pricePerMonth' : 75, 'maxMonths': 12},
'bronze': {'basePrice': 75, 'pricePerMonth' : 37.5, 'maxMonths': 2}
};
function setMonths(package)
{
var maxMonths = costs[package].maxMonths;
document.getElementById("months").innerHTML = ''; // Clear all options
for (var i = 1; i<=maxMonths; i++){
var opt = document.createElement('option');
opt.value = i;
opt.innerHTML = i + (i > 1 ? ' months' : ' month');
document.getElementById('months').appendChild(opt);
}
}
function calculatePrice()
{
var package = document.getElementById('packageType').value;
var months = document.getElementById('months').value;
var price = costs[package].basePrice + (costs[package].pricePerMonth * (months - 1));
document.getElementById('price').innerHTML = price.toFixed(2);
}
Working sample:
https://jsfiddle.net/td3j5frn/
Or, you may go, like:
//data model
var membershipPlans = {
silver: {'1mo': 150, '2mo': 225, '3mo': 300},
gold: {'1mo': 199, '2mo': 298.5, '3mo': 398}
};
//don't punish me for that with downvotes , please :)
Array.prototype.unique = function() {
const resArr = [];
this.forEach(entry => {
if(resArr.indexOf(entry) == -1) resArr.push(entry);
})
return resArr;
};
//populate the view with possible options
const inputFields = {
package: document.getElementById('package'),
duration: document.getElementById('duration')
};
const cost = document.getElementById('cost');
inputFields.package.innerHTML = Object.keys(membershipPlans).sort().reduce((options, option) => options+=`<option value="${option}">${option}</option>`,'<option value="" selected disabled></option>');
inputFields.duration.innerHTML = Object.values(membershipPlans).map(entry => Object.keys(entry)).flat().unique().reduce((options, option) => options+=`<option value="${option}">${option}</option>`,'<option value="" selected disabled></option>');
//listen for input changes and display the cost
Object.values(inputFields).forEach(inputField => {
inputField.addEventListener('change', ()=>
cost.innerHTML = Object.values(inputFields).every(inputField => inputField.value !='') ? membershipPlans[inputFields.package.value][inputFields.duration.value]+' £' : '- £')
});
<div id="wrapper">
<span>Pick your </span>
<br>
<label>package:</label>
<select id="package" class="calcInput"></select>
<label>duration:</label>
<select id="duration" class="calcInput"></select>
<br>
<span>Your cost is:</span>
<br>
<span id="cost">- £</span>
</div>
Related
I am looking to have two custom attributes for products, where the second custom attribute has unique options depending on the first attribute selected.
My particular circumstance is selling art that will have many different formats and sizes, where the price of the sizes will be different depending on which format is selected (IE: Print, Framed, Canvas, etc.).
The obvious alternative is to just have different product listings for each format, and not have the double drop down menu's. However, that is not ideally what I am looking to do.
This is the code provided in the documentation for a single select box and custom attribute:
<label>Frame color</label>
<select id="frame_color">
<option value="Black">Black</option>
<option value="Brown">Brown</option>
<option value="Gold">Gold</option>
</select>
<button
id="starry-night"
class="snipcart-add-item"
data-item-id="starry-night"
data-item-price="79.99"
data-item-url="/paintings/starry-night"
data-item-description="High-quality replica of The Starry Night by the Dutch post-impressionist painter Vincent van Gogh."
data-item-image="/assets/images/starry-night.jpg"
data-item-name="The Starry Night"
data-item-custom1-name="Frame color"
data-item-custom1-options="Black|Brown|Gold"
data-item-custom2-name="Gift note">
Add to cart
</button>
<script>
const button = document.querySelector('#starry-night')
const select = document.querySelector('#frame_color')
select.addEventListener('change', () => {
// Sets the default frame color when adding the item
button.setAttribute("data-item-custom1-value", select.value)
})
</script>
This can be done by having multiple products behind the scenes, but making it appear to the user that there is only one product (per item). Then, changing which products (and custom attribute selection boxes) are visible depending on the first selection box.
I am a novice so there may be a simpler way to accomplish this, but this is what I came up with and it works well. Also, I am using a little jQuery in this code so it will require modifications to work without it.
<style>
.hidden{
display:none;
}
</style>
<select id="item-1">
<option value="1">Type 1</option>
<option value="2">Type 2</option>
</select>
<div id="type-1-1" class="item-content-1">
<select id="size-1-1">
<option value="8x8 ($50)">8x8 ($50)</option>
<option value="12x12 ($100)">12x12 ($100)</option>
<option value="20x20 ($200)">20x20 ($200)</option>
</select>
<button id="add-to-cart-1-1" class="snipcart-add-item"
data-item-id="product-1-1"
data-item-price="0.00"
data-item-url="https://example.com"
data-item-description="Product 1 type 1 description"
data-item-image="/img.jpg"
data-item-name="Product 1 type 1"
data-item-custom1-name="Size"
data-item-custom1-options="8x8 ($50)[+50.00]|12x12 ($100)[+100.00]|20x20 ($200)[+200.00]"
data-item-custom1-value="8x8 ($50)"
data-item-custom1-required="true">Add To Cart
</button>
</div>
<div id="type-1-2" class="item-content-1 hidden">
<select id="size-1-2">
<option value="8x8 ($90)">8x8 ($90)</option>
<option value="12x12 ($170)">12x12 ($170)</option>
<option value="20x20 ($300)">20x20 ($300)</option>
</select>
<button id="add-to-cart-1-2" class="snipcart-add-item"
data-item-id="product-1-2"
data-item-price="0.00"
data-item-url="https://example.com"
data-item-description="Product 1 type 2 description"
data-item-image="/img.jpg"
data-item-name="Product 1 type 2"
data-item-custom1-name="Size"
data-item-custom1-options="8x8 ($90)[+90.00]|12x12 ($170)[+170.00]|20x20 ($300)[+300.00]"
data-item-custom1-value="8x8 ($90)"
data-item-custom1-required="true">Add To Cart
</button>
</div>
<select id="item-2">
<option value="1">Type 1</option>
<option value="2">Type 2</option>
</select>
<div id="type-2-1" class="item-content-2">
<select id="size-2-1">
<option value="8x8 ($50)">8x8 ($50)</option>
<option value="12x12 ($100)">12x12 ($100)</option>
<option value="20x20 ($200)">20x20 ($200)</option>
</select>
<button id="add-to-cart-2-1" class="snipcart-add-item"
data-item-id="product-2-1"
data-item-price="0.00"
data-item-url="https://example.com"
data-item-description="Product 2 type 1 description"
data-item-image="/img.jpg"
data-item-name="Product 2 type 1"
data-item-custom1-name="Size"
data-item-custom1-options="8x8 ($50)[+50.00]|12x12 ($100)[+100.00]|20x20 ($200)[+200.00]"
data-item-custom1-value="8x8 ($50)"
data-item-custom1-required="true">Add To Cart
</button>
</div>
<div id="type-2-2" class="item-content-2 hidden">
<select id="size-2-2">
<option value="8x8 ($90)">8x8 ($90)</option>
<option value="12x12 ($170)">12x12 ($170)</option>
<option value="20x20 ($300)">20x20 ($300)</option>
</select>
<button id="add-to-cart-2-2" class="snipcart-add-item"
data-item-id="product-2-2"
data-item-price="0.00"
data-item-url="https://example.com"
data-item-description="Product 2 type 2 description"
data-item-image="/img.jpg"
data-item-name="Product 2 type 2"
data-item-custom1-name="Size"
data-item-custom1-options="8x8 ($90)[+90.00]|12x12 ($170)[+170.00]|20x20 ($300)[+300.00]"
data-item-custom1-value="8x8 ($90)"
data-item-custom1-required="true">Add To Cart
</button>
</div>
<script>
var item_count = 2; //number of items in shop
var type_count = 2; //number of type subdivisions
var i = 1;
for (i = 1; i <= item_count; i++) {
const type_select = document.querySelector('#item-' + i);
const count = i
type_select.addEventListener('change', () => {
$('.item-content-' + count).addClass("hidden");
$('#type-' + count + "-" + type_select.value).removeClass("hidden");
});
var ii = 1;
for (ii = 1; ii <= type_count; ii++) {
const addToCart = document.querySelector('#add-to-cart-' + i + "-" + ii);
const size = document.querySelector('#size-' + i + "-" + ii);
size.addEventListener('change', () => {
addToCart.setAttribute("data-item-custom1-value", size.value);
});
};
};
</script>
I believe you can do this with data-item-custom1-value:
data-item-custom1-name="Color"
data-item-custom1-options="Blue|Dark Gray|Light Gray"
data-item-custom1-value="Dark Gray"
Then use Javascript to change the data-item-custom1-value when a select is changed to the value of the select.
Complete Example
<div>
<label for="color">Color</label>
<select name="color" id="color">
<option value="Blue">Blue</option>
<option value="Dark Gray">Dark Gray</option>
<option value="Light Gray">Light Gray</option>
</select>
</div>
<button id="poster-cart-btn" class="snipcart-add-item btn btn-dark"
data-item-id="1"
data-item-price="9.95"
data-item-url="/"
data-item-name="Poster"
data-item-image="img/poster.png"
data-item-description="A pretty poster"
data-item-custom1-name="Color"
data-item-custom1-options="Blue|Dark Gray|Light Gray"
data-item-custom1-value="Blue">
Add to cart
</button>
<script type="text/javascript">
window.addEventListener('load', function() {
document.getElementById('color').onchange = function() {
const val = document.getElementById('color').value;
document.getElementById('poster-cart-btn').setAttribute('data-item-custom1-value', val);
}
});
</script>
iam not realy good in js, is there anyway to give .setAttribute more then 1 value to altering the price? Thanks alot
<select id="size-2-2">
<option value="8x8 ($90)">8x8 ($90)</option>
<option value="12x12 ($170)">12x12 ($170)</option>
<option value="20x20 ($300)">20x20 ($300)</option>
</select>
<select id="color-2-3">
<option value="color_1 ($90)">8x8 ($90)</option>
<option value="color_2 ($170)">12x12 ($170)</option>
<option value="color_3 ($300)">20x20 ($300)</option>
</select>
<button id="add-to-cart-2-2" class="snipcart-add-item"
data-item-id="product-2-2"
data-item-price="0.00"
data-item-url="https://example.com"
data-item-description="Product 2 type 2 description"
data-item-image="/img.jpg"
data-item-name="Product 2 type 2"
data-item-custom1-name="Size"
data-item-custom1-options="8x8 ($90)[+90.00]|12x12 ($170)[+170.00]|20x20 ($300)[+300.00]"
data-item-custom1-value="8x8 ($90)"
data-item-custom1-required="true"
data-item-custom2-name="Color"
data-item-custom2-options="color_1 ($90)[+90.00]|color_2 ($170)[+170.00]|color_3($300)[+300.00]"
data-item-custom2-value="color_1 ($90)"
data-item-custom2-required="true">Add To Cart
</button>
...
addToCart.setAttribute("data-item-custom1-value", size.value);
addToCart.setAttribute("data-item-custom2-value", size.value);
...
Thanks a lot #justin I modify your way dirty and it works fine for me! Now snipcart snacks all the values from the select fields with one button. I know there is a better way to load "window.addEventListener" x times. Feel free to post a better and simpler solution.
<div>
<label for="color-1">Color 1</label>
<select name="Color select 1" id="color_1">
<option value="color_1_1">0</option>
<option value="color_1_2">+11</option>
<option value="color_1_3">+111</option>
</select>
<label for="color-2">Color 2</label>
<select name="Color select 2" id="color_2">
<option value="color_2_1">0</option>
<option value="color_2_2">+12</option>
<option value="color_2_3">+112</option>
</select>
<label for="color-3">Color 3</label>
<select name="Color select 3" id="color_3">
<option value="color_3_1">0</option>
<option value="color_3_2">+13</option>
<option value="color_3_3">-113</option>
</select>
</div>
<button id="poster-cart-btn" class="snipcart-add-item"
data-item-id="1"
data-item-price="0.00"
data-item-url="/"
data-item-name="Poster"
data-item-image="img/poster.png"
data-item-description="A pretty poster"
data-item-custom1-name="Color 1"
data-item-custom1-options="color_1_1|color_1_2[+11.00]|color_1_3[+111.00]"
data-item-custom1-value="color_1_1"
data-item-custom2-name="Color 2"
data-item-custom2-options="color_2_1|color_2_2[+12.00]|color_2_3[+112.00]"
data-item-custom2-value="color_2_1"
data-item-custom3-name="Color 3"
data-item-custom3-options="color_3_1|color_3_2[+13.00]|color_3_3[+113.00]"
data-item-custom3-value="color_3_1">
Add to cart
</button>
<script type="text/javascript">
window.addEventListener('load', function() {
document.getElementById('color_1').onchange = function() {
const val = document.getElementById('color_1').value;
document.getElementById('poster-cart-btn').setAttribute('data-item-custom1-value', val);
}
document.getElementById('color_2').onchange = function() {
const val = document.getElementById('color_2').value;
document.getElementById('poster-cart-btn').setAttribute('data-item-custom2-value', val);
}
document.getElementById('color_3').onchange = function() {
const val = document.getElementById('color_3').value;
document.getElementById('poster-cart-btn').setAttribute('data-item-custom3-value', val);
}
});
</script>
I'm trying to create a cost-calculator for my friend's carpet business website.
I don't know how to get both input fields and multiply them together to get the result/cost.
I'd like it so that a client chooses a carpet type - with cost per m2 associated with it
Then choose the size of the room.
The result would be the cost per m2 x m2 of the room.
I've created this horror show so far, it works for the first part - cost per m2, not the multiplication or size of room part though.
`<select id="classSelect" onchange="aFunction()">
<option value="0">Choose Flooring Type</option>
<option value="1">Vinyl</option>
<option value="2">Thick Carpet</option>
<option value="3">Standard Carpet</option>
<option value="4">Class 4 Cost 4</option>
<option value="5">Class 5 Cost 5</option>
</select>
<select id="size" onchange="bFunction()">
<option value="0">Choose Size</option>
<option value="3">3 Meters Squared</option>
<option value="5">5 Meters Squared</option>
<option value="10">10 Meters Squared</option>
<option value="15">15 Meters Squared</option>
<option value="20">20 meters squared</option>
</select>
<div id="result"></div>
<script>
function aFunction(){
classCost = Number(document.getElementById("classSelect").value);
fee = 5;
if (classCost > 0){
total = classCost + fee;
document.getElementById("result").innerHTML = total;
}else{
document.getElementById("result").innerHTML = ("Select Class");
}
}
</script>`
"I don't know how to get both inputted fields and multiply them together to get the result/cost."
It's not a full implementation of what you want, it's just a good point to start. Here I get values from two inputs, multiply them and write final value to the h1 tag (I didn't add any checks for NaN and so on, it's just a starter for you):
function calculate() {
var result = parseInt(document.getElementById('one').value) * parseInt(document.getElementById('two').value);
document.getElementsByTagName('h1')[0].innerText = result;
}
<input id="one">
<input id="two">
<button onclick="calculate()">Calculate</button>
<h3>Result of multiplication: </h3>
<h1>0</h1>
Update
"Any idea please what I'm missing here - jsfiddle.net/v1ncjkpw "
You just forgot to change function name and insert h1 tag. onchange event doesn't fire on jsfiddle for some reason (it's OK for jsfiddle), so here is the snippet with updated code:
function calculate() {
var result = parseInt(document.getElementById('classSelect').value) * parseInt(document.getElementById('size').value);
document.getElementsByTagName('h1')[0].innerText = result;
}
<select id="classSelect" onchange="calculate()">
<option value="0">Choose Flooring Type</option>
<option value="1">Vinyl</option>
<option value="2">Thick Carpet</option>
<option value="3">Standard Carpet</option>
<option value="4">Class 4 Cost 4</option>
<option value="5">Class 5 Cost 5</option>
</select>
<select id="size" onchange="calculate()">
<option value="0">Choose Size</option>
<option value="3">3 Meters Squared</option>
<option value="5">5 Meters Squared</option>
<option value="10">10 Meters Squared</option>
<option value="15">15 Meters Squared</option>
<option value="20">20 meters squared</option>
</select>
<h1>0<h1>
As what i understood from you question is that you want to multiple both selected values like (class+5) * size
function calculate(){
var classCost = Number(document.getElementById("classSelect").value);
if (classCost === 0){
document.getElementById("result").innerHTML = "Select Class";
return;
}
var roomSize = Number(document.getElementById("size").value);
if (roomSize === 0){
document.getElementById("result").innerHTML = "Select Size";
return;
}
var total = (classCost + 5) * roomSize;
document.getElementById("result").innerHTML = "Total Cost is " + total;
}
<select id="classSelect" onchange="calculate()">
<option value="0">Choose Flooring Type</option>
<option value="1">Vinyl</option>
<option value="2">Thick Carpet</option>
<option value="3">Standard Carpet</option>
<option value="4">Class 4 Cost 4</option>
<option value="5">Class 5 Cost 5</option>
</select>
<select id="size" onchange="calculate()">
<option value="0">Choose Size</option>
<option value="3">3 Meters Squared</option>
<option value="5">5 Meters Squared</option>
<option value="10">10 Meters Squared</option>
<option value="15">15 Meters Squared</option>
<option value="20">20 meters squared</option>
</select>
<div id="result"></div>
Please see the solution on fiddle
A very interesting thing hapens to my code.I have 3 different selects,one for years, the second for months and the third for days.I created options for the years and days via JS. My problem is my years list starts from the start point but dosn't end in the finish point I give,but when I'm changing the start point of j to 300 for instance, everything works perfectly.What is the reason or maybe my code is not correct? https://jsfiddle.net/arminemash/f9gy1p4L/15/
select{float:left}
#month,#days,input{display:none}
<body onload='addOptions()'>
<form action=''>
<select required id='year' class='selectOption' onchange='select(this)'>
<option value=""> Select year</option>
</select>
<select required id='month' class='selectOption' onchange='select(this)'>
<option value=""> Select month</option>
<option value="January">January</option>
<option value="February">February</option>
<option value="March">March</option>
<option value="April">April</option>
<option value="May">May</option>
<option value="June">June</option>
<option value="July">July</option>
<option value="August">August</option>
<option value="September">September</option>
<option value="October">October</option>
<option value="November">November</option>
<option value="December">December</option>
</select>
<select required id='days' class='selectOption' onchange='select(this)'>
<option value="">Select Day</option>
</select>
<input type="submit" class='selectOption' onclick='getDate()'>
</form>
</body>
function addOptions(){
var x= document.getElementById('year');
var y = document.getElementById('days');
for(var i=1900,j=1;i<3000,j<=31;i++,j++){
var option1 = document.createElement("option");
var option2 = document.createElement("option");
option1.text =i;
x.add(option1);
option2.text =j;
y.add(option2);
}
}
var i=0;
function select(par){
var x=document.getElementsByClassName('selectOption');
if( par.selectedIndex !== "0"){
x[i+1].style.display='block';
i++;
collectData.push(par.value);
}
}
The problem is your for loop. for(var i=1900,j=1;i<3000,j<=31;i++,j++) this will stop when j reaches 31. What you need is two for loops one for days and one for years. I edited your fiddle here.
I'm trying to calculate the number of nights between two selected days of the week using jQuery for a booking system, to specify which days of the week people can arrive and depart on. I have two dropdowns, one for arrival day and one for departure day:
<select required="required" class="daypicker" id="arrivalday" name="arrivalday">
<option></option>
<option value="1">Monday</option>
<option value="2">Tuesday</option>
<option value="3">Wednesday</option>
<option value="4">Thursday</option>
<option value="5">Friday</option>
<option value="6">Saturday</option>
<option value="7">Sunday</option>
</select>
<select required="required" class="daypicker" id="departureday" name="departureday">
<option></option>
<option value="1">Monday</option>
<option value="2">Tuesday</option>
<option value="3">Wednesday</option>
<option value="4">Thursday</option>
<option value="5">Friday</option>
<option value="6">Saturday</option>
<option value="7">Sunday</option>
</select>
If either of the dropdowns change, it should calculate the number of nights as follows:
arrival = Monday
departure = Friday
number of nights = 4
arrival = Monday
departure = Monday
number of nights = 7
arrival = Friday
departure = Monday
number of nights = 3
This is what I have so far, but nothing is happening:
$(document).ready(function(){
$(".daypicker").change(function(){
var arrivalday = $("#arrivalday").val();
var departureday = $('#departureday').val();
if (arrivalday == departureday){
$('#numnights').html('7');
} else if (arrivalday < departureday) {
$('#numnights').html(departureday - arrivalday);
} else {
$('#numnights').html(arrivalday- departureday - 1);
}
}).change();
});
Found the issue, the selects are displayed after a user selects an option, so I moved the code into the change function of that option and everything worked as expected.
You already got it, you just needed to create the container for the output (the numnights element).
Anyway the code is a little bit cleaner in this way:
$(document).ready(function(){
$(".daypicker").on('change', function(){calculateNights();});
});
function calculateNights() {
var arrivalday = $("#arrivalday").val();
var departureday = $('#departureday').val();
var numberNights = departureday - arrivalday;
numberNights = (numberNights < 1) ? numberNights + 7 : numberNights;
$("#numNights").html(numberNights);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<select required="required" class="daypicker" id="arrivalday" name="arrivalday">
<option></option>
<option value="1">Monday</option>
<option value="2">Tuesday</option>
<option value="3">Wednesday</option>
<option value="4">Thursday</option>
<option value="5">Friday</option>
<option value="6">Saturday</option>
<option value="7">Sunday</option>
</select>
<select required="required" class="daypicker" id="departureday" name="departureday">
<option></option>
<option value="1">Monday</option>
<option value="2">Tuesday</option>
<option value="3">Wednesday</option>
<option value="4">Thursday</option>
<option value="5">Friday</option>
<option value="6">Saturday</option>
<option value="7">Sunday</option>
</select>
<hr>
<div id="numNights"></div>
Hope it helps!
I'm trying to limit the number of options based on another selection. For instance in this example "How many credits is the class you skipped?" should be limited to equal or less than the previous question "How many total credits are you taking this semester?". So if I'm only taking 9 credits on semester the second question of how many credits I'm skipping should be equal or less than the 9 credits for the whole semester.
Any help will be greatly appreciated.
Here is the jsfiddle: http://jsfiddle.net/k7tDP/1/
Here is the JS:
function calculateCost() {
'use strict';
// enter annual tuition
var $annualTuition = parseInt($('#annual_tuition').val());
// tuition per semester
var semesterTuition = Math.round($annualTuition / 3);
// total number of credits for semester
var $semesterCredits = parseInt($('#semester_credits').val());
// cost of a single credit
var singleCreditCost = semesterTuition / $semesterCredits;
// total credits for class being skipped
var $skippedTotalCredits = parseInt($('#skipped_total_credits').val());
// total cost for class being skipped
var skippedTotalCreditsCost = $skippedTotalCredits * singleCreditCost;
// number of times skipped class meets per week
var $skippedWeekDays = parseInt($('#skipping_class_meet').val());
// from date
var fromDate = $('#from').datepicker('getDate');
// to date
var toDate = $('#to').datepicker('getDate');
// calculate number of weeks in date range (semester) using 'from / to' dates
var skippedWeeks = Math.ceil((toDate - fromDate) / (1000 * 7 * 60 * 60 * 24));
console.log(skippedWeeks);
// total number of days in semester for class being skipped
//var $skippedTotalDays = parseInt($('#skipped_total_days').val());
var skippedTotalDays = $skippedWeekDays * skippedWeeks;
// (total cost of class) / (total number of class days in semester) = cost of class
var skippedSingleClassCost = skippedTotalCreditsCost / skippedTotalDays;
return skippedSingleClassCost.toFixed(2);
}
$(function() {
'use strict';
$('#from').datepicker({
defaultDate: '+1w',
changeMonth: true,
numberOfMonths: 1,
onSelect: function() {
//toDate = $(this).datepicker('getDate');
}
});
$('#to').datepicker({
defaultDate: '+1w',
changeMonth: true,
numberOfMonths: 1,
onSelect: function() {
//fromDate = $(this).datepicker('getDate');
}
});
$('#cost').on('click', function() {
$('.costFigure').fadeIn('fast');
$('#costTotal').html(calculateCost());
});
});
Here is the html:
<form id="costForm" action="#" onsubmit="#">
<div>
<label for="annual_tuition">What is your annual tuition (estimated)?</label>
<div class="styled_select">
<select name="annual_tuition" id="annual_tuition" value="tuition amount" autofocus>
<option value="0"> </option>
<option value="5000">$5,000</option>
<option value="10000">$10,000</option>
<option value="15000">$15,000</option>
<option value="20000">$20,000</option>
<option value="25000">$25,000</option>
<option value="30000">$30,000</option>
<option value="35000">$35,000</option>
<option value="40000">$40,000</option>
<option value="45000">$45,000</option>
<option value="50000">$50,000</option>
</select>
</div>
</div>
<div>
<label for="semester_credits">How many total credits are you taking this semester?</label>
<div class="styled_select">
<select name="semester_credits" id="semester_credits" value="" tabindex="2">
<option value="0"> </option>
<option value="3">3 credits</option>
<option value="6">6 credits</option>
<option value="9">9 credits</option>
<option value="12">12 credits</option>
<option value="13">13 credits</option>
<option value="14">14 credits</option>
<option value="15">15 credits</option>
<option value="16">16 credits</option>
<option value="17">17 credits</option>
<option value="18">18 credits</option>
</select>
</div>
</div>
<div>
<label for="skipped_total_credits">How many credits is the class you skipped?</label>
<div class="styled_select">
<select name="skipped_total_credits" id="skipped_total_credits" value="" tabindex="2">
<option value="0"> </option>
<option value="3">3 credits</option>
<option value="6">6 credits</option>
<option value="9">9 credits</option>
<option value="12">12 credits</option>
<option value="13">13 credits</option>
<option value="14">14 credits</option>
<option value="15">15 credits</option>
<option value="16">16 credits</option>
<option value="17">17 credits</option>
<option value="18" disabled>18 credits</option>
</select>
</div>
</div>
<div>
<label for="skipping_class_meet">How many times a week does the class you skipped meet?</label>
<div class="styled_select">
<select name="skipping_class_meet" id="skipping_class_meet" value="" tabindex="2">
<option value="0"> </option>
<option value="1">1 time a week</option>
<option value="2">2 times a week</option>
<option value="3">3 times a week</option>
<option value="4">4 times a week</option>
<option value="5">5 times a week</option>
</select>
</div>
</div>
<div class="dateRange clearfix">
<label>Between what months are you enrolled in this class?</label>
<div style="width: 48%; float: left;">
<label for="from">From:</label>
<input type="text" id="from" name="from">
</div>
<div style="width: 48%; float: right;">
<label for="to">To:</label>
<input type="text" id="to" name="to">
</div>
</div>
<div>
<button id="cost" type="button">Calculate</button>
</div>
<div class="costFigure">
<h1>your missed class cost you $<span id="costTotal"></span></h1>
</div>
</form>
On change of your dropdown fire a onchange trigger and on the basis of values make the 2nd dropdown enable or disabled.
$("#semester_credits").change(function () {
var $this=this;
$("#skipped_total_credits").children().each(function(){
$(this).attr("disabled",parseInt($this.value) < parseInt(this.value));
});
});
Check the fiddle here
EDIT
$this.value contains the value selected from "semester_credits" dropdown, now For each child of "skipped_total_credits", I am checking if that value is less than the children value then make it disabled, i.e attr("disabled", true) else make that children enabled.
I've created a quick function to help you out, there may be a neater way to do this, but it does the job quite nicely!
Onchange of the element #semester_credits I grab the value (number of semesters credits and then loop over the next select box and remove the ones that have a higher value that the chosen one, I use a global var to cache the removed options in case the user changes their minds and we need to add them back in.
$(function () {
var savedOpts = "";
$('#semester_credits').change(function() {
//Add all options back in;
if( savedOpts ) {
$('#skipped_total_credits').append(savedOpts);
savedOpts = "";
}
//Return false if blank option chosen;
if( $(this).val() === "0" )
return false;
var chosenCreds = parseInt($(this).val());
$('#skipped_total_credits option').each(function() {
var thisCred = parseInt($(this).val());
if(thisCred > chosenCreds) {
//Remove
savedOpts += $(this)[0].outerHTML;
$(this).remove();
}
});
});
Here an updated fiddle
p.s the example Kai Hartmann suggests is also a nice way to achieve this.
If you want the drop-down list for a question to change based on previous answer, you need to add an onchange event to each select element which would update another drop-down. This should then call a function which removes or adds elements in your form.
Otherwise, you can add a validation function for your Calculate button.