...

View Full Version : Update price and item number on option select



steamngn
07-06-2007, 09:12 PM
Hi Javascript Gurus!!
(I think I'm in the right place with this one...)
I am building an online store, and I have a web page in PHP that displays the item and dynamically builds <SELECT> options for those items that have them. This part is working fine...
What I am looking to do is set it up so that when a customer makes a selection in one of the options (there could be 0-3 options for any given item) the page refreshes or somehow updates the price for that item, and also appends a 2 digit code to the item number. I can make the option values the price, the 2 digit item number, or both if need be. The form for this mess is for a paypal shopping cart, so the form action is already pointed to their site. Can someone help this PHP guy who knows squat about JS:confused:

2reikis
07-06-2007, 10:50 PM
You should have at least a rudimentary grasp of Javascript before you start this. What you want to do involves defining the onChange attribute of the select. You'll need to create a subroutine that analyzes the form and sets the price each time a selection changes.

You define the onChange attribute in the HTML select tag....



<form name="form1" action=....>
<select name="slcMonth" onChange="fnChkForm()">
<option value="January">January</option>
<option value="12.50">February</option>
.
.
.
</form>
<div id="lyrInfo"></div>


and, in the head section...


<script language = "javascript">
function fnChkForm() {
f=document.form1
if (f.slcMonth.options[f.selectedIndex].value = "January" {
document.getElementByID("lyrInfo").innerHTML = "$42.00"
}
}
</script>

or


<script language = "javascript">
function fnChkForm() {
f=document.form1
myVal = f.slcMonth.options[f.slcMonth.selectedIndex].value
numPrice = +42 + myVal
document.getElementById("lyrInfo").innerHTML = "$"+numPrice
}
</script>

Of course, you can run a subroutine before the form is submitted and nix the submission, or modify the form fields before you submit by defining a function for the form tag.


<form name="form1" action="...." onSubmit="return fnSubmit()">
.
.
.
</form>

The return bit is important. If fnSubmit returns false, the form won't submit. Within fnSubmit, you can set the value of your hidden form fields based on the final selections just before submitting the form. If it's all good, just return true and the form submits.

HTH

2reikis

steamngn
07-07-2007, 01:41 PM
Hey 2reikis,
what fun would it be knowing what I'm doing?:D
Ok, I get the basic idea here, and I have a question before I proceed. Would it be better/benficial/why bother to build a Javascript array using the PHP first, and then reference the different combinations of values that way? The reason I ask is since I want to update the price AND append the item number, don't we need a way to reference both columns for each option? Or should I shut up and code?:rolleyes:
Andy

2reikis
07-08-2007, 08:27 AM
Hi Steamngn,
Sorry for the long delay. The weekend, you know.

I would always recommend a plan of action before proceeding. In fact, since I haven't seen any code, I have only a theoretical knowledge of what you want to do so plan is all I can help with.

As for your very valid question, I think the answer would be interactivity. PHP knows the data, but not the choices. That happens client-side and PHP doesn't go there. And, of course, you can always interleave PHP and Javascript.


<?php
$fruits='';
$price='';
while ($row_Fruits=mysql_fetch_array($conn)) {
$fruits .= $row_Fruits['name'].',';
$price .= $row_Fruits['price'].',';
}
$fruits = substr($fruits, 0, -1);
$price = substr($fruits, 0, -1);
echo <<<EOS
<script language='javascript'>
strFruits = new Array("$fruits");
numPrice = new Array("$price");
</script>
EOS;
?>
</head>
<body>
<select name="slcFruits">
<script language = "javascript">
for (i=0;i<=strFruits.length;i++) {
document.write("<option value='"+numPrice[i]+"'>"+strFruit+"</option>";
}
</script>
</select>

This seperates the page from the data. If you decide to add more fruit later, just add it to the database and it will appear in the page. The code to make an associative array (fruit["name"]="banana", fruit["price"]=4.20) is not too different.

Does this sound like a plan? You can even have a third parallel array with the two character option code that would be referenced by the select option


strOpCode[document.form1.slcFruit.selectedIndex]

HTH

2reikis

glenngv
07-08-2007, 09:02 PM
You can dynamically change the form action based on user action.

function updateItem(oSel){

//...

oSel.form.action="yourUrl.php";
oSel.form.submit();
}

<form name="frm" action="">
<select name="selItem" onchange="updateItem(this);">
...
</select>
<input type="submit" value="Submit to Paypal" onclick="this.form.action='paypalUrl';" />
</form>

steamngn
07-09-2007, 02:44 PM
Good morning all!

Sorry for the long delay. The weekend, you know.
Never a problem! Personal before volunteerism is A-ok!:D :D
I spent the weekend reading up on Javascript, trying to get a grasp of how it works a bit and some of the syntax. I can see already that I will have syntax errors what with the similar-but-not-so-similar PHP and Javascript syntax.
As for your code, I THINK it is coming close.. let me re-explain myself (with a bit more knowledge now) and see if it helps:
The PHP SELECT query for this page joins table ITEMS and table ITEM_GRIDS; ITEMS has relevant item information and ITEM_GRIDS has grid info for each item. The query result looks like this:


item_no grid_1_indx grid_2_indx grid_3_indx prc_1 prc_2 prc_3
-------------------------------------------------------------------------
123 small white short sleeve 1.00 1.25 0.00
123 medium white short sleeve 1.00 1.25 1.00
123 large white short sleeve 1.00 1.00 1.00
123 small black short sleeve 1.00 1.00 1.00
123 medium black short sleeve 1.00 1.50 1.50
123 large black short sleeve 1.50 1.50 1.50
123 small white long sleeve 1.50 1.50 1.50
etc...
What I am doing on the PHP side is dynamically building the <SELECT> options with a while loop, and these options (if they exist; not every item has options) are inside the dynamically built form. As for what needs to happen when there are options:
Options are not exactly the correct term; requirements would be more like it. After the customer makes the required selections, a few things need to happen. Firstly is the price needs to be appended (item price + prc_1 + prc_2 + prc_3) each time the customer changes a selection. Second the item number needs to be appended with the option code (item_no 123 needs to become 1230100 if the first option in the grid is selected, 1230200 if second, etc.. this code is also a column in the grid table and is in the query). Finally when the customer clicks "add to cart" on the form the concatenated item number and the concatenated price need to be sent in the hidden fields in the form to paypal. Lastly (and this is optional but desirable) it would be nice if the options where also concatenated and sent in one of the hidden optional fields (small white short sleeve) as well. This would provide a good reference at checkout and also could be passed backwards as well. The only other thing that I see as a point of interest/concern is what to do if people don't have javascript enabled? Is there a way to check for that and warn the user if need be? Or am I off base on that?
I REALLY appreciate the help from everyone. This is a new territory for me, and the guidance is GREATLY appreciated!
Andy

Something more! After more thought (and more reading) something obvious just hit me:
In the table ITEM_GRIDS there is a unique column ITEM_GRID_INDX where the value is the item number with the appopriate two-digit grid code appended to it, like 1230100 for item 123 with grid one selected and grid two not selected and no grid three.
SO....
If we use that as the option value, then can't we use that same number to ID each row in our array and pull data accordingly?
I have no idea how to do that, but it sounds like this would be the most logical step...
So now I have used PHP to create a javascript array that looks like this:

<script language="javascript">
pricearray = new Array("
1230100,4.75,Solid White,~,~
1230200,1,Solid Bone,~,~
1230300,0,Solid Bisque,~,~
1230400,0,Shell Rose,~,~
1230500,0,Dove Gray,~,~
1230101,9.75,Solid White,Textured,~
")
</script>
the first field is the item number+grid id, the second is the total price for the option combination, then the first option description, then the second option description and finally the third option description.
Now for the problem:
What I would need is code so that each time an option is changed the code looks at ALL the current values of all the options, concatenates them to the item number, finds the approprite row in the array that matchaes that number, and then returns the price value+the item price for display (and into the hidden form field), returns the array item number into the hidden item number field and returns the last three fields coupled together into the hidden custom field.
Can this be done?

steamngn
07-09-2007, 08:35 PM
Ok,
I am going to take a real half-@$$ed attempt at the beginning of this (Dad always told me to be brave!:D )
Does this look like it makes any sense at all:

<script="javascript">
function setoptions()
{
for(var i=0;i<=pricearray.length-1;i++{
if (form.option1.value == <<<how would I reference the first column in the array here>>>)
form.amount.value = <<<how do I reference the array amount column here>>>
<<<and how do I display this value on the page??>>>
}
After playing around with this a bit I notice that my array did not seem well-formatted. I changed the code to output this:

<script language="javascript">
pricearray = new Array()
'BS-25150100,4.75,Solid White,~,~'
'BS-25150200,1,Solid Bone,~,~'
'BS-25150300,0,Solid Bisque,~,~'
'BS-25150400,0,Shell Rose,~,~'
'BS-25150500,0,Dove Gray,~,~'
</script>
And I smashed my head against the desk until my Young-Frankenstien function looked like this:

<script type="text/javascript">
function setOptions()
{
for(var i=0;i<=pricearray.length-1;i++){
if(form.checkout.item_number.value+form.checkout.option1.value+form.checkout.option2.value+form.chec kout.option3.value == pricearray[0])
{
form.amount.value = pricearray[1]
}
}
}
</script>

It doesn't seem to work, but I'm having a helluva lot of fun trying!
Andy

2reikis
07-09-2007, 10:20 PM
Given this:



<script language="javascript">
pricearray = new Array("
1230100,4.75,Solid White,~,~
1230200,1,Solid Bone,~,~
1230300,0,Solid Bisque,~,~
1230400,0,Shell Rose,~,~
1230500,0,Dove Gray,~,~
1230101,9.75,Solid White,Textured,~
")
</script>


<script="javascript">
function setoptions()
{
fEle=document.form1.slcOptions
// may help to shorten our code.
// This is the select element.
// form1 is the form name
for(var i=0;i<=pricearray.length-1;i++) {
if (f.options[f.selectedIndex].value == pricearray[i][0]) {
document.form1.amount.value = pricearray[i][1]
//Short answer
obj = document.getElementById("dTotal");
obj.innerHTML = pricearray[i][2]+"<br>$"+pricearray[i][1]
}

is, at least, a start. There's a nice quick tutorial on access select elements here (http://www.javascriptkit.com/javatutors/combos3.shtml)

But I'm not sure I understand the requirements.

This grid here....


item_no grid_1_indx grid_2_indx grid_3_indx prc_1 prc_2 prc_3
-------------------------------------------------------------------------
123 small white short sleeve 1.00 1.25 0.00
123 medium white short sleeve 1.00 1.25 1.00
123 large white short sleeve 1.00 1.00 1.00
123 small black short sleeve 1.00 1.00 1.00
123 medium black short sleeve 1.00 1.50 1.50
123 large black short sleeve 1.50 1.50 1.50
123 small white long sleeve 1.50 1.50 1.50
etc...

How many selects does it output? And what does each select contain? I'm having trouble with the 0.00 in prc_3 for line one. Does that mean an item number 123 in style "short sleeve" is free, or is there a base price that prc_1, prc_2, and prc_3 get added to?

steamngn
07-09-2007, 10:57 PM
Hey 2reikis,
Hope you had a great holiday weekend....
Ok, first things first:

How many selects does it output?
There is only one select query, and it will output one row for each iteration of the grid for an item. (I have no control over how the data is stored, as it is export/import from third party apps) It works like this: There are 3 possible dimentions to the grid, and a row will be output for each dimention x dimention x dimention.
So if there are 3 entries in dimention 1 (small med large) and two in dimention 2 (black white) the query will return 6 rows, 1 row for each of the following:
small,black
small,white
med,black
med,white
large,black
large,white
This is kinda crappy, I know, but it is what I have to work with. I can manipulate the query as needed to add or remove columns from the result set, but the grid return will still contain the number of rows.

I'm having trouble with the 0.00 in prc_3 for line one. Does that mean an item number 123 in style "short sleeve" is free, or is there a base price that prc_1, prc_2, and prc_3 get added to?
Lets fix the naming and things will be much clearer:
prc_1,prc_2 and prc_3 should be GRID_PRC_1,GRID_PRC_2 and GRID_PRC_3. Their default is 0.00; values greater than 0 will only be present if there is an extra charge for that dimention option. PRC_1 is the base price of the item, and whenever an option is changed we need to:

PRC_1+GRID_PRC_1+GRID_PRC_2+GRID_PRC_3
Since each row in the result set is a unique combination of available options, I "did the math" and added the values together into the second column of the array. When I posted that "grid" of data earlier I mearly entered some numbers to give you an idea of what was there; that info is fictitious, but 0 is possible.
As for the data itself:
The data is truly dynamic, with items added/removed daily. Any item may have 0 to 3 dimentions in a grid if options are needed. So I need to code in a way that will allow no options and will still work with three options! yippee!!
I moved the function code to be built dynamically when the PHP is run, as we need to add only those options that are present to the item number. The problem with that is when there is only one option I need to add "00" to the end of the item number+option1 string. When there are two or three options I only need to add all the options to the string. It never ends with thing!!:eek:
Hope I cleared up some more of this!
Andy

BTW!! the name of the form is "checkout"... don't we need that in there somewhere?

2reikis
07-10-2007, 04:46 AM
My first thought is why not build the variable part of the part number into the value of the select option. That would give us a single step to get the final part number and you could keep most of the logic server side where you seem to be more comfortable.

so the select looks like


<select name = slcBS-251>
<option value = 50100>Small, Black</option>
<option value = 50200>Small, White</option>
</select>

Oh.... We need the price in there, too, don't we?

Two ways come to mind; parallel arrays for the part number and aggregate price differential (which you can calculate server side on a per option basis), or putting it into the option value.


<option value = "4.25:50100">Small, Black</option>
<option value = "2.75:50200">Small, White</option>

parseFloat on this value would ignore anything after the first non-numeric character and return 4.25 and 2.75 respectively. You could retrieve the variable part number using the string function .split(":") something like...


<javascript language="javascript">
f=document.checkout
s=f.slcBS-251
sVal = s.options[s.selectedIndex].value
priceTotal = priceArray["BS-251"] + parseFloat(sVal)
desc = sVal.split(":")
document.getElementById["final"].innerHTML = desc[1]+"<br>$"+priceTotal
f.amount.value = priceTotal
</script>
So your query should return a set that includes the base part number, the variable part of the part number, the aggregate price difference for that part number with those modifiers and the aggregate description for the option statement. Can you get a sample result set with those requirements?

I'll check back in later tonight and tomorrow morning.

2reikis

steamngn
07-10-2007, 01:38 PM
Good Morning!(well, here anyway:D )

My first thought is why not build the variable part of the part number into the value of the select option.
I had this same thought, but then if there are THREE options for an item (remeber,that is a possibility) then the option list will be reeeeaaaaally long, and I'm sure that will cause more shoppers to make mistakes when they go to purchase.

Oh.... We need the price in there, too, don't we?
Yeah, that is another little "issue". Adding to the option value is fine, and that sure could be a way to finish this up....

...and you could keep most of the logic server side where you seem to be more comfortable.
Weeeelllll..... while my PHP is getting quite good, any of this is proving to be challenging and enjoyable, so this is really not a concern (as long as I don't burn out my friends :p !)
As far as getting a result set...

<script language="javascript">
pricearray = new Array()
'BS-25150100,4.75,Solid White,~,~'
'BS-25150200,1,Solid Bone,~,~'
'BS-25150300,0,Solid Bisque,~,~'
'BS-25150400,0,Shell Rose,~,~'
'BS-25150500,0,Dove Gray,~,~'

</script>
<script type="text/javascript">
function setOptions()
{
f=document.checkout
for(var i=0;i<=pricearray.length-1;i++){
if(BS-2515+ f.option1.options[f.option1.selectedIndex].value+00 = pricearray[i][0])
{
form.amount.value = pricearray[i][1]
document.getElementById("sellprc").innerHTML = "$"+pricearray[i][1]
}
}
}

</script>
This is the returned code along with the returned array. I was futzing around with a simple script that would actually make the <DIV>sellprc show the price (I was ELATED!!), but I cannot get it to work with the loop and the array. Can you see something screwy with this? My instincts tell this should be close...:rolleyes:

As for the followup code you posted, are we getting off the idea of building an array and pulling the data we need from that? It seems like that would be the most flexible answer should a change be needed, but I am in your trusting hands as far as viability and stability goes...
One of the reasons I like server side for the bulk of web design is the low client overhead. ISP servers are usually more than robust enough to handle this type of work in a quick fashion, while far too many client machines are not much more than a coffee maker with a promotion :eek:! Building up the javascript and then letting the client just switch the variables around seems like the best workflow way to go....
It is interesting to note all of the PayPal Cart-related forum posts out there, and how many of them struggle with just what we're doing. The answers are always aimed at one specific piece of this (like add a description to a custom field in the cart, but not the item number or cost), and then later the same user is posting on the PayPal site about why they can't do the next piece and how it is PayPal that has designed poorly! I say let's build the client side so that it can be modified without too much trouble and then the masses will rejoice! (oh, brother...)
:D

2reikis
07-10-2007, 09:03 PM
Just to let you know... I'm noodlin' this. I have to say, it's a fun project.

We might start with your array. It's good as far as it goes, but to be of use to us, it will have to be taken a step further (and some syntax cleaned up)


pricearray = new Array('BS-25150100,4.75,Solid White,~,~',
'BS-25150200,1,Solid Bone,~,~',
'BS-25150300,0,Solid Bisque,~,~',
'BS-25150400,0,Shell Rose,~,~',
'BS-25150500,0,Dove Gray,~,~')

so as you see we've put each line into it's own array item

now we need to split the array into another dimension


for (i=0; i<pricearray.length; i++) {
pricearray[i] = pricearray[i].split(",")
}

Now we have a two dimensional array with

pricearray[0][0] = 'BS-25150100'
pricearray[0][1] = '4.75'
pricearray[0][2] = 'solid white'
pricearray[0][3] = '~'
pricearray[0][4] = '~'


and so on. Is this on track?

How about a list with three modifiers so we can work up a display function based on how many selects will be needed.

2reikis

steamngn
07-11-2007, 01:06 PM
... I'm noodlin' this. I have to say, it's a fun project.

Yes, it is! I seem to be thinking about it every time I am sitting quiet for a minute...
Ok, after some housecleaning, I now have this:

<script language="javascript">
pricearray = new Array(
'BS-25150100,224.44,Solid White,~,~',
'BS-25150200,220.69,Solid Bone,~,~',
'BS-25150300,219.69,Solid Bisque,~,~',
'BS-25150400,219.69,Shell Rose,~,~',
'BS-25150500,219.69,Dove Gray,~,~'
)
</script>
<script type="text/javascript">
function setOptions()
{
f=document.checkout
for(var i=0;i<=pricearray.length-1;i++){
pricearray[i] = pricearray[i].split(",")
if(BS-2515+ f.option1.options[f.option1.selectedIndex].value+00 = pricearray[i][0])
{
form.amount.value = pricearray[i][1]
document.getElementById("sellprc").innerHTML = "$"+pricearray[i][1]
}
}
}
</script>
Couple of things:
1) Notice that the dollar value has changed in pricearray[1]; i forgot to add the base price before :o !
2)Did I add the second level array split correctly?
3)No, it still doesn't work.
4)I will build up a three-option item today, but follow along for a second---
The PHP for this page is fairly complex, and it builds each <SELECT>and option dynamically as needed. since this part was already done, it was a fairly simple task to insert the javascript IF statement into the PHP and build it up dynamically. Hense if we have only one option it returns

if(BS-2515+ f.option1.options[f.option1.selectedIndex].value+00 = pricearray[i][0])
and if there are more than one:

if(BS-2515+ f.option1.options[f.option1.selectedIndex].value+ f.option2.options[f.option2.selectedIndex].value = pricearray[i][0])
and this can go on infinitely. Since we only will ever match one row and one row only in the array we only need to build one IF statement ( I think; I'm going out on a javascript limb here!:D )
One thing else that will need answering: How do I get the <DIV> to show the base price on page load or show something like "you haven't select your options" when not all of the options have been set yet? Minor, but it is one of the straggling bits...
Keep on noodlin'!!

10:39EST 07/11/07

Ok, as promised, the three-option code including the entire form:
The code:

<script language="javascript">
pricearray = new Array('BS-1515010101,195.6,Dove Gray,Brass,Polished',
'BS-1515010102,195.6,Dove Gray,Brass,Matte',
'BS-1515010201,185.6,Dove Gray,Chrome,Matte',
'BS-1515010202,185.6,Dove Gray,Chrome,Matte',
'BS-1515010301,205.6,Dove Gray,Stainless,Polished',
'BS-1515010302,205.6,Dove Gray,Stainless,Matte',
'BS-1515020101,195.6,White,Brass,Polished',
'BS-1515020102,195.6,White,Brass,Matte',
'BS-1515020201,185.6,White,Chrome,Polished',
'BS-1515020202,185.6,White,Chrome,Matte',
'BS-1515020301,205.6,White,Stainless,Polished',
'BS-1515020302,205.6,White,Stainless,Matte',
'BS-1515030101,205.6,Arctic Granite,Brass,Polished',
'BS-1515030102,205.6,Arctic Granite,Brass,Matte',
'BS-1515030201,195.6,Arctic Granite,Chrome,Polished',
'BS-1515030202,195.6,Arctic Granite,Chrome,Matte',
'BS-1515030301,215.6,Arctic Granite,Stainless,Matte',
'BS-1515030302,215.6,Arctic Granite,Stainless,Matte')
</script>
<script type="text/javascript">
function setOptions()
{
f=document.checkout
for(var i=0;i<=pricearray.length-1;i++){
pricearray[i] = pricearray[i].split(",")
if(BS-1515+ f.option1.options[f.option1.selectedIndex].value+form.checkout.option2.value+form.checkout.option3.value == pricearray[i][0])
{
form.amount.value = pricearray[i][1]
document.getElementById("sellprc").innerHTML = "$"+pricearray[i][1]
}
}
}

</script>
and the form:

<form target="_self" action="https://www.paypal.com/cgi-bin/webscr" method="post"><center>
<input type="hidden" name="cmd" value="_cart">
<input type="hidden" name="business" value="service@michaelsappliance.com">
<input type="image" src="https://www.paypal.com/en_US/i/btn/view_cart_02.gif" border="0" name="submit" alt="Make payments with PayPal - it's fast, free and secure!">
<input type="hidden" name="display" value="1">
</center></form>
<br>
<form name="checkout" method="post" action="https://www.paypal.com/cgi-bin/webscr">
<center>Quantity:<br><select name="quantity" >
<option selected value="1">1</option>
<option value="2">2</option>
<option value="3">3</option>

<option value="4">4</option>
<option value="5">5</option>
<option value="6">6</option>
<option value="7">7</option>
<option value="8">8</option>
<option value="9">9</option>
<option value="10">10</option>
</select><br>
<input type="hidden" name="add" value="1">
<input type="hidden" name="cmd" value="_cart">

<input type="hidden" name="business" value="service@michaelsappliance.com">
<input type="hidden" name="item_name" value="Swanstone Classic 15x15x6">
<input type="hidden" name="item_number" value="BS-1515">
<input type="hidden" name="amount" value="185.60">
<input type="hidden" name="no_shipping" value="0.00">
<input type="hidden" name="handling" value="0.00">
<input type="hidden" name="no_note" value="1">
<input type="hidden" name="lc" value="US">
<input type="hidden" name="return" value="http://www.yoursite.com/thankyou.htm">
<input type="hidden" name="undefined_quantity" value="1">
<input type="hidden" name="currency_code" value="USD">
<input type="hidden" name="tax" value="0">
<input type="hidden" name="bn" value="PP-ShopCartBF">
<input type="hidden" name="custom" value="">
Choose your Color:<br><select name="option1" onchange="setOptions()">
<option value="00">--Please Select--</option>

<option value="01">Dove Gray</option>
<option value="02">White</option>
<option value="02">White</option>
<option value="03">Arctic Granite(+$10.00)</option>
<option value="03">Arctic Granite(+$10.00)</option>
</select><br>

Choose your Trim:<br><select name="option2">
<option value="00">--Please Select--</option>
<option value="01">Brass(+$10.00)</option>

<option value="02">Chrome</option>
<option value="03">Stainless(+$20.00)</option>
</select><br>

Choose your Finish:<br><select name="option3">
<option value="00">--Please Select--</option>
<option value="01">Polished(+$5.00)</option>
<option value="02">Matte(+$12.00)</option>
</select><br>

<br><input type="image" src="http://images.paypal.com/en_US/i/btn/x-click-but22.gif" border="0" name="submit" width="87" height="23" alt="Make payments with PayPal - it's fast, free and secure!">

</center></form>

steamngn
07-11-2007, 11:03 PM
UPDATES!!
Phew, what a day...
After reading a TON of stuff on javascript arrays and playing around a bit, I've come up with the following:

<script language="javascript" type="text/javascript">
var pricearray = [['BS-25150100','224.44','Solid White','~','~'],['BS-25150200','220.69','Solid Bone','~','~'],['BS-25150300','219.69','Solid Bisque','~','~']]
</script><script type="text/javascript">
function setOptions(){
f=document.checkout
l="BS-2515"+f.option1.value+"00"

for(var i=0;i<=pricearray.length-1;i++){
if (f.option1.value>"00"){
myVal = l
document.getElementById("sellprc").innerHTML = myVal
}else if (f.option1.value=="00"){
document.getElementById("sellprc").innerHTML = "No Options Selected!"
}
}
}

</script>

This is almost sorta working! It sets the <DIV> element correctly, but the IF statement is wrong. Right now it is simply looking at the raw value for option1 (there is only one is this test) and displaying the var l. Var l is the correct index we need for the array, but I cannot get it to pass it in to the array and return the correct price. I've changed the array syntax around to the literal coding (not sure why, but the javascript forums seem to say that this is better) and I can reference array elements using pricearray[0][0] syntax, but I cannot get this to display using pricearray[i][0]...:confused:
Does this help?
Andy

2reikis
07-12-2007, 02:14 AM
Let's work with this for just a sec as I ponder the overall.

Your array function looks good. You might think of seperating it at the unquoted commas for readability, but hey, it's working, right?


var pricearray = [
['BS-25150100','224.44','Solid White','~','~'],
['BS-25150200','220.69','Solid Bone','~','~'],
['BS-25150300','219.69','Solid Bisque','~','~']
]

the main thing is, you've discovered how to make a multi-dimensional array, on the fly, and all at once.

:D Hey, I'm learning too!

Next there's this line...


if (f.option1.value>"00"){

Since we're dealing with strings, it's probably best to go with Javascript's not-equal operator to avoid gremlins.


if (f.option1.value != "00") {

Also, you need to start thinking of select tags as arrays with the options as the members. It's really an object. The object has a property selectedIndex that points to which of it's options is currently selected. The object also has a collection called options that contains option objects. To get to the final bit of juice that we want, we need to go a little deeper.


if (f.option1.options[f.selectedIndex].value != "00") {

is how to get the value of the selected option. This is different than posted forms. With a posted form being processed by PHP, the choices have been made and $_POST['option1'] has been resolved to a single value. In the browser, nothing's set in stone till the user clicks submit.

Also, why not just use the else statement. Since we're dealing with either/or how about


for(var i=0;i<=pricearray.length-1;i++){
if (f.option1.options[f.option1.selectedIndex].value!="00"){
myVal = pricearray[i][1]
document.getElementById("sellprc").innerHTML = l + "<br>" + "$" + myVal }
else
{
document.getElementById("sellprc").innerHTML = "No Options Selected!"
}
}

more to come later tonight. Boss is calling

2reikis

isshin
07-12-2007, 08:45 AM
that was tedious but thanks!

steamngn
07-12-2007, 01:50 PM
Ah yes....
The select tag stuff is still a bit fuzzy, but I'm getting it. I was ripping the code down to the basics to see if I could figure out why it doesn't work, hence the line:

if (f.option1.value>"00"){
Aside from poor syntax, it is also incorrect. What needs to happen is:

for(var i=0;i<=pricearray.length-1;i++){
if ("BS-2515"+f.option1.options[f.option1.selectedIndex].value+"00"==pricearray[i][0]){
myVal = pricearray[i][1]
document.getElementById("sellprc").innerHTML = l + "<br>" + "$" + myVal } else
{
document.getElementById("sellprc").innerHTML = "No Options Selected!"
}


}

So that when an option is changed, the function loops through the array of arrays, and IF one of the array[0] values matches the item number/option value string (in this case "BS-25150100") THEN set our <DIV> and related hidden field values to array[i][whatever field is needed].
WHAT I HAVE FOUND OUT THIS MORNING:
This line:

if ("BS-2515"+f.option1.options[f.option1.selectedIndex].value+"00"!=pricearray[i][0])
allows the function to work, bypassing the ELSE portion. Since we know that

("BS-2515"+f.option1.options[f.option1.selectedIndex].value
parses out a string that matches the values in the various pricearray[0] fields, there must be something wrong with the loop code. Also of interest is the fact that

myVal = pricearray[i][1]
is always returning the value for pricearray[3][1] regardless of which option is selected, and so is another indicator that the trouble here is with the loop.
I was wondering if we should be using a WHILE loop instead and then BREAK when we hit an array match, but I'm still reading about loops and trying to drink enough coffee to understand what the h&!! I'm reading:D !

steamngn
07-12-2007, 07:10 PM
How about....
well....
perhaps........

I GOT IT!!!!:eek:
Looky here:

<script type="text/javascript">
function setOptions(){
f=document.checkout
l="$219.69"//the base price of the item (loaded at runtime from PHP)
//set up the loop
index=0
while(index<pricearray.length){
//check if the passed values exist in the array
if ("BS-2515"+f.option1.options[f.option1.selectedIndex].value+"00"==pricearray[index][0]){
//set our variables
myVal = pricearray[index][1]
break;//end the loop if a match is found
}
index++
}
//if we have a valid match,display it and set our hidden variables
if((myVal!="a")&&(f.option1.options[f.option1.selectedIndex].value!="00")){
document.getElementById("sellprc").innerHTML = "$"+ myVal+" each"
document.checkout.amount.value = myVal
}
//if the user choose "--please select--" in a option box, cry foul!
else if(f.option1.options[f.option1.selectedIndex].value=="00"){
document.getElementById("sellprc").innerHTML = "Please Select a color!"
}
//otherwise just show the damned price already!
else{
document.getElementById("sellprc").innerHTML = l+" each"
}
//reset the variables(so we can test for no matches after the loop)
myVal="a"
}
</script>

Using the WHERE loop instead of a FOR loop doesn't make much difference, but having the ability to advance the counter wherever may be handy, so I left it. This is working like a charm, and it should allow pulling any field from any array/array to move accordingly.
I CANNOT BELIEVE IT!!:eek:
So first, see anything in there that is a no-no?
and second, how do you reference a button on the form to make it disabled if the customer has not selected an option(s)?

WOOHOOO!!!

2reikis
07-12-2007, 11:48 PM
Excellent. Some things are coming together now.

What you've come up with looks good so far. But the way you have this coded, the missing parts of the product ID are supplied by the select options and I haven't seen a mySQL query that supplies this information. In other words, if you have a shirt, product #123, and that shirt comes in white and black, don't white and black have codes? So if white is 10 and black is 20, the modified product ID would be 12310 for a white shirt. And if it comes in small, medium and large (say 100,200, and 300) then a small, black would be 12320100. That way when we build our options list, we can compare baseID+option1+option2+option3 to pricearray[0][0] and see if there's a match. Can we get a result set that has this info:


product ID price base ID code1 code2 code3 desc1 desc2 desc3
12301101 123.45 123 01 10 1 white short small
12302102 123.45 123 02 10 2 black short medium
12302101 125.34 123 02 10 1 black short small
12301203 127.56 123 01 20 3 white long large



Then we can use our pricearray to build the selects dynamically. Anything in pricearray[][3] that's not '~' get's put in the options list for slcOption1, pricearray[][4] goes into slcOption2 and so on.

Is this making sense, or do I need to noodle more?

2reikis

steamngn
07-13-2007, 01:04 PM
Good morning!
The item number portion is actually covered by the not-so-good 3rd party app; seems they got something right. I was inadvertently leaving it out of my posts, sorry!:

item_no grid_1_indx grid_2_indx grid_3_indx prc_1 prc_2 prc_3
-------------------------------------------------------------------------
123010101 small white short sleeve 1.00 1.25 0.00
123020101 medium white short sleeve 1.00 1.25 1.00
123030101 large white short sleeve 1.00 1.00 1.00
123010201 small black short sleeve 1.00 1.00 1.00
123020201 medium black short sleeve 1.00 1.50 1.50
123030201 large black short sleeve 1.50 1.50 1.50
123010102 small white long sleeve 1.50 1.50 1.50
etc.....
Each of the three options is a two-digit code, and the appropriate code combination is concatenated on the end of the item number for each row in the grid. This comes from the app, so all we need to do is take our item number, add the appropriate two-digit code(s) to the end, and compare it to the array for a match. The PHP code is building the javascript code, so dynamically it sets up how many option codes go on the end of the script and whether or not the "00" needs to be on the end (if only one option). I tested this a bit last night, and it seems to be working!! WOW! Still up on a cloud about that...:D
One thing that I thought about along with the button disable thing:
There is a quantity <select> on this form, and I would like a simple little script to display the price*quantity when the quantity changes. That should be easy, but is there a way to call that script FROM this one we've been working on, or does it need to be integrated? Remember that the price changes in this script, and this script will not even be in the page of an item that has no options (the PHP leaves it out).
What do you think? I will post the script code later today after I test it a bit more, and we'll move forward...

2reikis
07-14-2007, 07:38 AM
So if I understand it, the last 6 digits make up the three possible options (or 00 if there is no option)? Is that correct?

steamngn
07-14-2007, 01:43 PM
Morning!
Well, not quite, but close. Here is how it works in entirety:
We are joining several tables in our query:
ITEMS <<table of all items, with or without options>>
ITEM_CATEGORIES <<table of categories that items belong to(for sorting) keyed by ITEM_NO to ITEMS>>
ITEM_GRIDS <<table of item options if they exist, keyed by ITEM_NO to ITEMS>>

ITEMS will have item number 123 and all of the relevant item info (description,base price (or only price if no options),etc..):

ITEM_NO PRC DESCR
--------------------------------
123 9.99 hoozit
Now, here is where it gets silly. Lets say item 123 has only 1 option; Color. There are three colors available: Black, White and Yellow. ITEM_GRIDS will look like this:

ITEM_NO GRID_ID GRID_DIM_1 GRID_1_PRC
------------------------------------------------------
123 1230100 Black 0.00
123 1230200 White 0.00
123 1230300 Yellow 1.00

Notice that the grid code is 4 digits; the first two are the index for GRID_DIM_1, and the second two are just padding. Don't ask me why the vendor put them there, but they are unique to only single option items. Notice also that "Yellow" (1230300) has a 1.00 additional charge. So the price for this item is ITEM.PRC+ITEM_GRID_1_PRC or 10.99, while the other colors use the same math but are 9.99.

NOW!! If there are two or three options, there are no "00" padding at all:


ITEM_NO GRID_ID GRID_DIM_1 GRID_1_PRC GRID_DIM_2 GRID_2_PRC
--------------------------------------------------------------------------
456 4560101 Black 0.00 Small 0.00
456 4560102 Black 0.00 Large 2.00
456 4560201 White 0.00 Small 0.00
456 4560202 White 0.00 Large 2.00
456 4560301 Yellow 1.00 Small 0.00
456 4560302 Yellow 1.00 Large 2.00
Notice there is no padding in the GRID_ID (This company MUST sniff glue!). Now you also see that there is a 2.00 charge for large items, and we need to now do PRC+GRID_1_PRC+GRID_2_PRC to get the correct amount for the item. Adding a third grid is the same scenario, and two more digits are added to the end of GRID_ID. Also not that the only time GRID_ID ends in "00" is when there is only one option; otherwise the index always starts with "01".

NOW!!! The web page <body> is built completely using PHP at runtime; I loop through the returned set for an item (remember, this is after passing through all the categories and finally picking a single item to view/purchase) and build up the image page, options and the cart for for paypal. This is working fine, and it is fairly simple to grab any one query values and embed it into our javascript code as needed.
AND!! I went WAAAAAAAAAAAAAAAAAAAAAAAAYYYY out on a limb yesterday, and tried my hand at adding a little price update code to the quantity option. IT WORKED THE FIRST TIME!!! Welll.... almost:o ...
Here is the code as it stands today:

<script type="text/javascript">
var myVal;
var optprc=0;
var Prctot;
var prct;
var l=219.69;//The base price of the item (loaded at runtime as a numeral)
function setOptions(){
f=document.checkout
//set up the loop
index=0
while(index<pricearray.length){
//Check if the passed values exist in the array
if("BS-2515"+f.option1.options[f.option1.selectedIndex].value+"00"==pricearray[index][0]){
//set our variables
myVal = pricearray[index][1]
optprc = myVal
break;//end the loop if a match is found
} else {
myVal=0
}
index++
}
//if we have a valid match,display it and set our hidden variables
if((myVal!=0)&&(f.option1.options[f.option1.selectedIndex].value!="00")){
document.getElementById("sellprc").innerHTML = "$" + myVal+" each"
document.checkout.amount.value = f.quantity.options[f.quantity.selectedIndex].value * myVal
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is $" + prct.toFixed(2)
}
//if the user has not chosen an option, cry foul!
else if((f.option1.options[f.option1.selectedIndex].value=="00")){
var msg="The base price for this item is $"+l+"<br>Please select your "
{if((f.option1.options[f.option1.selectedIndex].value=="00")){
msg+="Color to view the price for this item."
}
}
document.getElementById("sellprc").innerHTML = msg
document.getElementById("totprc").innerHTML = "Options not selected!<br>Price totals will display<br>when all options are set"
}
//otherwise just show the price already!
else {
document.getElementById("sellprc").innerHTML = "$"+l+" each"
prct = f.quantity.options[f.quntity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is $" +prct.toFixed(2)
}
//reset the variables(so we can test for no matches after the loop)
myVal=0
}
function setPrice(){
f=document.checkout
//set our variables
Prctot = f.quantity.options[f.quantity.selectedIndex].value * l
if(optprc!=0){
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
} else {
prct = Prctot
}
document.getElementById("totprc").innerHTML = "Total price is $" + prct.toFixed(2)
}

</script>
And you can see this code if you browse here:
http://michaelsappliance.com/itemdisplay.php?item=BS-2515
This code is also built up using PHP at runtime, and the various checks and options are added accordingly(This item has only one option, but if there are more the appropriate f.optionx elements are added. This is also working ok, and the various iterations seem error free).
Here is what is NOT working:
If you use the Color option to select a color, and then go back and select "--Please Select---, you will see that under the image there is a warning about not having selected the proper options. You will also see this waring under the quantity option. BUT!! If you change the quantity at this point, under the quantity option it will calculate the new price BASED ON THE LAST PRICE BUILT DURING THE OPTION SELECT. What I would like it to do is keep the warning message there until the options change. I know that the second function I added is not referencing the first one correctly, but I am stumped about how to fix it.
I also would like the "Add to cart" button disabled when the page loads AND there are options, so that the user cannot add the item until the options are set. This button also needs to be enabled when the page loads and there are no options. Of course, that is assuming that this can even be done...
Once these last pieces are done then all that is left is to fininsh up the beautifying of the page and it is "live" time!
Does any of this make sense? Should I be shipping you coffee or margarita mix??;)
Andy

2reikis
07-16-2007, 11:36 AM
My doctor says I've had enough coffee for this life. I'm experimenting with different teas. (more like tease). Luckily, he hasn't said anything about the margaritas (yay!).

The button is easy to enable or disable.
f.submit.disabled = true will disable the button in IE and Firefox.

The code you have there is good, but I think it could be simplified. If you use just one sub for the onChange handler for both selects, you can enable/disable the "Add to cart" button based on whether you get a valid price. That way, all the logic for setting the price, form fields and status divs is in one place.

Question: how will this code change if there are two options? How about three? Is there a way to code the page such that one page can handle all three eventualities?

I think there is. We should be able to add our options up by checking for the existence of our selects. if there's a select for option 1, add it to the base code. If there's a select for option 2, add that. Otherwise, add "00". If there's a select for option 3, add it.


strTemp = baseCode;
// check for option 1
if (f.option1) {
strTemp += f.option1.value;
// only check for option2 if there is an option 1
if (f.option2) {
strTemp += f.option2.value;
}
else
{
// add mass silliness if there's no option 2 but there is an option 1
strTemp += "00";
}
if (f.option3) {
strTemp += f.option3.value;
}
myVal = 0;
for (i=0;i<pricearray.length;i++) {
if (pricearray[i][0] == strTemp)
myVal = pricearray[i][1];
}
if (myVal!=0) {
//update price
//enable button
}
else
{
// show message
// disable button
}

Can we build something around this?

2reikis

steamngn
07-16-2007, 02:21 PM
Happy Monday!(Like that could be without coffee:D )..
Ok, I learnded a coople tingies:
The "add to cart" button wasn't disabling when I first used your code; the input type was 'image', and this doesn't disable like input type 'submit'. I changed the button around, and it works hunky-dory! So what did I do? Decide not to use it....
I added a little form validation function to make sure the options (if they exist) are chosen before the form can submit, which seems to me like a better idea than just disabling the button. A little alert window pops up if an option isn't selected. I like this approach, and it also allows using image submit styles should that become an issue.
As for what/how the code for multiple options looks like:

<script type="text/javascript">
var myVal;
var optprc=0;
var Prctot;
var prct;
var l=185.60;//The base price of the item (loaded at runtime as a numeral)
function setOptions(){
f=document.checkout
//set up the loop
index=0
while(index<pricearray.length){
//Check if the passed values exist in the array
if("BS-1515"+f.option1.options[f.option1.selectedIndex].value+f.option2.options[f.option2.selectedIndex].value+f.option3.options[f.option3.selectedIndex].value==pricearray[index][0]){
//set our variables
myVal = pricearray[index][1]
optprc = myVal
break;//end the loop if a match is found
} else {
myVal=0
}
index++
}
//if we have a valid match,display it and set our hidden variables
if((myVal!=0)&&(f.option1.options[f.option1.selectedIndex].value!="00")&&(+f.option2.options[f.option2.selectedIndex].value!="00")&&(+f.option3.options[f.option3.selectedIndex].value!="00")){
document.getElementById("sellprc").innerHTML = "$" + myVal+" each"
document.checkout.amount.value = myVal
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is<br> $" + prct.toFixed(2)
}
//if the user has not chosen an option, cry foul!
else if((f.option1.options[f.option1.selectedIndex].value=="00")||(f.option2.options[f.option2.selectedIndex].value=="00")||(f.option3.options[f.option3.selectedIndex].value=="00")){
var msg="The base price for this item is $"+l+"<br>Please select your "
{if((f.option1.options[f.option1.selectedIndex].value=="00")&&(f.option2.options[f.option2.selectedIndex].value!="00")&&(f.option3.options[f.option3.selectedIndex].value!="00")){
msg+="Color to view the price for this item."
}
else if((f.option1.options[f.option1.selectedIndex].value=="00")&&(f.option2.options[f.option2.selectedIndex].value=="00")&&(f.option3.options[f.option3.selectedIndex].value=="00")){
msg+="Color, Trim and Finish to view the price for this item."
}
if((f.option1.options[f.option1.selectedIndex].value!="00")&&(f.option2.options[f.option2.selectedIndex].value=="00")&&(f.option3.options[f.option3.selectedIndex].value=="00")){
msg+="Trim and Finish to view the price for this item."
}
else if((f.option1.options[f.option1.selectedIndex].value!="00")&&(f.option2.options[f.option2.selectedIndex].value!="00")&&(f.option3.options[f.option3.selectedIndex].value=="00")){
msg+="Finish to view the price for this item."
}
else if((f.option1.options[f.option1.selectedIndex].value!="00")&&(f.option2.options[f.option2.selectedIndex].value=="00")&&(f.option3.options[f.option3.selectedIndex].value!="00")){
msg+="Trim to view the price for this item."
}
else if((f.option1.options[f.option1.selectedIndex].value=="00")&&(f.option2.options[f.option2.selectedIndex].value=="00")&&(f.option3.options[f.option3.selectedIndex].value!="00")){
msg+="Color and Trim to view the price for this item."
}
else if((f.option1.options[f.option1.selectedIndex].value=="00")&&(f.option2.options[f.option2.selectedIndex].value!="00")&&(f.option3.options[f.option3.selectedIndex].value=="00")){
msg+="Trim to view the price for this item."
}
}
document.getElementById("sellprc").innerHTML = msg
document.getElementById("totprc").innerHTML = "Options not selected!<br>Price totals will display<br>when all options are set"
}
//otherwise just show the price already!
else {
document.getElementById("sellprc").innerHTML = "$"+l+" each"
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is<br> $" +prct.toFixed(2)
}
//reset the variables(so we can test for no matches after the loop)
myVal=0
}
function setPrice(){
f=document.checkout
//set our variables
Prctot = f.quantity.options[f.quantity.selectedIndex].value * l
if(optprc!=0){
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.checkout.amount.value = optprc
} else {
prct = Prctot
document.checkout.amount.value = l
}
document.getElementById("totprc").innerHTML = "Total price is<br> $" + prct.toFixed(2)
}
function Validate()
{
f=document.checkout
if ((f.option1.value=="00")|| (f.option2.value=="00")|| (f.option3.value=="00")) { alert( "Please choose your options befor adding this item to your cart." )
return false; }
return true;
}
</script>
The above code is for an item with all three options. What happens here is the javascript functions themselves are being built using PHP. Since we can test to see if the option exists when the page is requested, we can add to the script options as needed. In my code above I am building the various combinations of selected/not selected and returning an error accordingly. This is pretty long winded!! It does allow for PHP to insert custom descriptions based on item info into the code, but I'm sure there is a more elegant way to write this. Actually this isn't very much code PHP-wise, and it is all in one page. When a customer goes to the online store, they first load webstore.php, which shows all of the item categories. When a category is selected the same page reloads with whatever subcategories are available. When a category/subcategory is selected that contains items, THEN itempdisplay.php is loaded (the page we're working on). This page will show all of the items in the given category, and reloads with a given item when one is selected (The specific code we're working on for this page). The entire PHP portion of this page is only 350 lines including queries and connect strings, etc.. and this is with each line of the javascript laid out like(this is the end portion of the function(s) we're building):

if (($item != "") && ($option1)){
$js6 .= "){\n";
$js7 .= "){\n";
$js1 .= "==pricearray[index][0]){\n";
$js1 .= "//set our variables\n";
$js1 .= "myVal = pricearray[index][1]\n";
$js1 .= "optprc = myVal\n";
$js1 .= "break;//end the loop if a match is found\n";
$js1 .= "} else {\n";
$js1 .= "myVal=0\n";
$js1 .= "}\n";
$js1 .= "index++\n";
$js1 .= "}\n";
$js1 .= "//if we have a valid match,display it and set our hidden variables\n";
$js1 .= $js6;
$js1 .= "document.getElementById(\"sellprc\").innerHTML = \"$\" + myVal+\" each\"\n";
$js1 .= "document.checkout.amount.value = myVal\n";
$js1 .= "prct = f.quantity.options[f.quantity.selectedIndex].value * optprc\n";
$js1 .= "document.getElementById(\"totprc\").innerHTML = \"Total price is<br> $\" + prct.toFixed(2)\n";
$js1 .= "}\n";
$js1 .= "//if the user has not chosen an option, cry foul!\n";
$js1 .= " else ". $js7;
$js1 .= "var msg=\"The base price for this item is $\"+l+\"<br>Please select your \"\n";
$js1 .= "{if((f.option1.options[f.option1.selectedIndex].value==\"00\")";
if(!$option2){
$js1 .= "){\n";
$js1 .= "msg+=\"" . $js5e . " to view the price for this item.\"\n";
$js1 .= "}\n";
} else if(($option2) && (!$option3)){
$js1 .= "&&(f.option2.options[f.option2.selectedIndex].value!=\"00\")){\n";
$js1 .= "msg+=\"" . $js5e . " to view the price for this item.\"\n";
$js1 .= "} else if((f.option1.options[f.option1.selectedIndex].value!=\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js3e . " to view the price for this item.\"\n";
$js1 .= "} else if((f.option1.options[f.option1.selectedIndex].value==\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js5e . " and " . $js3e . " to view the price for this item.\"\n";
$js1 .= "}\n";
} else if(($option2) && ($option3)){
$js1 .= "&&(f.option2.options[f.option2.selectedIndex].value!=\"00\")&&(f.option3.options[f.option3.selectedIndex].value!=\"00\")){\n";
$js1 .= "msg+=\"" . $js5e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "else if((f.option1.options[f.option1.selectedIndex].value==\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")&&(f.option3.options[f.option3.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js5e . ", " . $js3e . " and " . $js4e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "if((f.option1.options[f.option1.selectedIndex].value!=\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")&&(f.option3.options[f.option3.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js3e . " and " . $js4e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "else if((f.option1.options[f.option1.selectedIndex].value!=\"00\")&&(f.option2.options[f.option2.selectedIndex].value!=\"00\")&&(f.option3.options[f.option3.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js4e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "else if((f.option1.options[f.option1.selectedIndex].value!=\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")&&(f.option3.options[f.option3.selectedIndex].value!=\"00\")){\n";
$js1 .= "msg+=\"" . $js3e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "else if((f.option1.options[f.option1.selectedIndex].value==\"00\")&&(f.option2.options[f.option2.selectedIndex].value==\"00\")&&(f.option3.options[f.option3.selectedIndex].value!=\"00\")){\n";
$js1 .= "msg+=\"" . $js5e . " and " . $js3e . " to view the price for this item.\"\n";
$js1 .= "}\n";
$js1 .= "else if((f.option1.options[f.option1.selectedIndex].value==\"00\")&&(f.option2.options[f.option2.selectedIndex].value!=\"00\")&&(f.option3.options[f.option3.selectedIndex].value==\"00\")){\n";
$js1 .= "msg+=\"" . $js3e . " to view the price for this item.\"\n";
$js1 .= "}\n";
}
$js1 .= "}\n";
$js1 .= "document.getElementById(\"sellprc\").innerHTML = msg\n";
$js1 .= "document.getElementById(\"totprc\").innerHTML = \"Options not selected!<br>Price totals will display<br>when all options are set\"\n";
$js1 .= "}\n";
$js1 .= "//otherwise just show the price already!\n";
$js1 .= "else {\n";
$js1 .= "document.getElementById(\"sellprc\").innerHTML = \"$\"+l+\" each\"\n";
$js1 .= "prct = f.quantity.options[f.quantity.selectedIndex].value * optprc\n";
$js1 .= "document.getElementById(\"totprc\").innerHTML = \"Total price is<br> $\" +prct.toFixed(2)\n";
$js1 .= "}\n";
$js1 .= "//reset the variables(so we can test for no matches after the loop)\n";
$js1 .= "myVal=0\n";
$js1 .= "}\n";
}
$js1 .= "function setPrice(){\n";
$js1 .= "f=document.checkout\n";
$js1 .= "//set our variables\n";
$js1 .= "Prctot = f.quantity.options[f.quantity.selectedIndex].value * l\n";
$js1 .= "if(optprc!=0){\n";
$js1 .= "prct = f.quantity.options[f.quantity.selectedIndex].value * optprc\n";
$js1 .= "document.checkout.amount.value = optprc\n";
$js1 .= "} else {\n";
$js1 .= "prct = Prctot\n";
$js1 .= "document.checkout.amount.value = l\n";
$js1 .= "}\n";
$js1 .= "document.getElementById(\"totprc\").innerHTML = \"Total price is<br> $\" + prct.toFixed(2)\n";
$js1 .= "}\n";
$js1 .= "function Validate()\n";
$js1 .= "{\n";
$js1 .= "f=document.checkout\n";
if(($option1)||($option2)||($option3)){
if($option1){
$js1 .= " if ((f.option1.value==\"00\")";
}
if($option2){
$js1 .= "|| (f.option2.value==\"00\")";
}
if($option3){
$js1 .= "|| (f.option3.value==\"00\")";
}
$js1 .= ") { alert( \"Please choose your options befor adding this item to your cart.\" )\n";
$js1 .= " return false; }\n";
}
$js1 .= " return true;\n";
$js1 .= "}\n";
$js1 .="</script>\n";

So pretty much what you are asking here:

Question: how will this code change if there are two options? How about three? Is there a way to code the page such that one page can handle all three eventualities?
Is just what is happening in the PHP code on load. This allows the server to do all the work, and the end user machine can be a real loafer and still load up in a timely manner.

OK, So now for the next step! Before we condense/fix up my ugly code, how about we get the last little piece working. The form validation fixed the disable button issue (ok, replaced the button issue!), so the only thing that is still not working is the price changing when quantity changes and there are unset options:

Here is what is NOT working:
If you use the Color option to select a color, and then go back and select "--Please Select---, you will see that under the image there is a warning about not having selected the proper options. You will also see this waring under the quantity option. BUT!! If you change the quantity at this point, under the quantity option it will calculate the new price BASED ON THE LAST PRICE BUILT DURING THE OPTION SELECT. What I would like it to do is keep the warning message there until the options change. I know that the second function I added is not referencing the first one correctly, but I am stumped about how to fix it.
Iff we sore this out then we will have a complete piece of code that can be cleaned up and organized, and that will be a wonderful thing!
Andy

2reikis
07-17-2007, 11:03 AM
<yawn>Hi Andy,
I work for myself so every day is potentially Monday and every day is potentially Saturday. Most days are a little of both.

I think the answer to our last sticky wicket is in code segregation. You really only want one place in the code where the selects are analyzed and you really only get one piece of critical info from it. So put it into a sub all it's own and then return either false, or the selling price. Then call that sub from wherever it's needed. This means only one place to trouble shoot when something goes wonky.


function fnChkSelects() {
myVal = false
f=document.checkout
//set up the loop
index=0
while(index<pricearray.length){
//Check if the passed values exist in the array
if("BS-1515"+f.option1.options[f.option1.selectedIndex].value+f.option2.options[f.option2.selectedIndex].value+f.option3.options[f.option3.selectedIndex].value==pricearray[index][0]){
//set our variables
myVal = pricearray[index][1]
}
index++
}
return myVal
}

Then the onChange for each select goes to a much shortened function


function fnSlcChange() {
f=document.checkout
sellPrc = fnChkSelects()
if (sellPrc) {
// display sellPrc in div "sellprc"
// display sellPrc * quantity in div "totprc"
} else {
// display "you haven't finished choosing"
}
}

and your validate function calls the same sub.


function fnValidate() {
f = document.checkout
sellPrc = fnChkSelects()
if (sellPrc) {
f.amount.value=sellPrc
return true
} else {
alert("keep shakin' the bush!")
return false
}
}

Whaddaya tink?

2reikis

steamngn
07-17-2007, 01:02 PM
Self employed, eh? I know that all too well..
I work here for an Appliance retailer, and then travel an hour each way to the Taekwondo school that I own to teach. Every other day is like 18- 18 1/2 hours.... would not trade it for the world!
Ok, I get the idea of the sub, and I will try to get it laid out today. I added a simple line to the curent code to disable the quantity select when options aren't set; it isn't really the best way, but it allowed us to move forward and get some of the online store up and running. Go check it out:
http://www.michaelsappliance.com/webstore.php
looks pretty good for a 1st attempt so far!
Andy

steamngn
07-25-2007, 05:13 PM
I'm baaack...
Finally had a chance to get back to this a bit, and I'm having trouble. I just can't seem to get the function/sub sorted out. here is the code that is working, but by disabling the quantity:

<script language="javascript">
var pricearray = [['KSDB-25180100','195.02','Solid White','~','~'],
['KSDB-25180200','195.02','Solid Bone','~','~'],
['KSDB-25180300','195.02','Solid Bisque','~','~'],
['KSDB-25180400','195.02','Shell Rose','~','~'],
['KSDB-25180500','195.02','Dove Gray','~','~']]
</script>
<script type="text/javascript">
var myVal;
var optprc=0;
var Prctot;
var prct;
var item;
var l=195.02;//The base price of the item (loaded at runtime as a numeral)
function setOptions(){
f=document.checkout
//set up the loop
index=0
while(index<pricearray.length){
//Check if the passed values exist in the array
if("KSDB-2518"+f.option1.options[f.option1.selectedIndex].value+"00"==pricearray[index][0]){
//set our variables
myVal = pricearray[index][1]
item = pricearray[index][0]
optprc = myVal
break;//end the loop if a match is found
} else {
myVal=0
}
index++
}
//if we have a valid match,display it and set our hidden variables
if((myVal!=0)&&(f.option1.options[f.option1.selectedIndex].value!="00")){
document.getElementById("sellprc").innerHTML = "$" + myVal+" each"
document.checkout.amount.value = myVal
document.checkout.os0.value = item
document.checkout.on0.value = f.option1.options[f.option1.selectedIndex].text
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is<br> $" + prct.toFixed(2)
document.checkout.quantity.disabled=false
}
//if the user has not chosen an option, cry foul!
else if((f.option1.options[f.option1.selectedIndex].value=="00")){
var msg="The base price for this item is $"+l+"<br>Please select your "
{if((f.option1.options[f.option1.selectedIndex].value=="00")){
msg+="Color to view the price for this item."
}
}
document.getElementById("sellprc").innerHTML = msg
document.getElementById("totprc").innerHTML = "Options not selected!<br>Price totals will display<br>when all options are set"
document.checkout.amount.value = optprc
document.checkout.quantity.disabled=true
}
//otherwise just show the price already!
else {
document.getElementById("sellprc").innerHTML = "$"+l+" each"
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.getElementById("totprc").innerHTML = "Total price is<br> $" +prct.toFixed(2)
document.checkout.amount.value = optprc
document.checkout.quantity.disabled=false
}
//reset the variables(so we can test for no matches after the loop)
myVal=0
}
function setPrice(){
f=document.checkout
//set our variables
Prctot = f.quantity.options[f.quantity.selectedIndex].value * l
if(optprc!=0){
prct = f.quantity.options[f.quantity.selectedIndex].value * optprc
document.checkout.amount.value = optprc
} else {
prct = Prctot
document.checkout.amount.value = l
}
document.getElementById("totprc").innerHTML = "Total price is<br> $" + prct.toFixed(2)
}
function Validate()
{
f=document.checkout
if ((f.option1.value=="00")) { alert( "Please choose your options befor adding this item to your cart." )
return false; }
return true;
}

</script>
I've played around and around, but I must be misunderstanding how to get this into the new code as you suggested. I will keep playing around and let you know....
Andy
BTW--- sent out some reputations today. Almost forgot:o !!



EZ Archive Ads Plugin for vBulletin Copyright 2006 Computer Help Forum