Press enter to skip the top menu

JavaScript

Decisions

Learning Outcomes

On completion of this section you will know how to:

Go to top

Introduction

In all aspects of life we make decisions. An example is: if the buses are running we shall go into town, otherwise we shall study. In programming we have to make decisions as well or to be more precise we shall tell the computer how to make decisions.

To demonstrate this we shall modify the way we calculate the tax. When introducing our first programme we had a simple flat tax rate of 25%, which was fine as far as learning how a basic programme worked. In this example we shall take a more realistic view of the payroll application. We will create a tax regime where if the gross is below 500 we have a flat 25% rate. On the other hand if the gross is more than 500 then we pay 25% on the first 500 and 33% or the remainder. A few examples will help to explain this further.

A gross of 460 will be taxed at 25% since it is less than 500 and thus the tax will be 25% of 460, which is 115. This will give a net of 345.

A gross of 600 is greater than 500 and so it will be taxed as 25% of 500 and 33% of the remainder. 25% of 500 will be 125. The remainder will be 600 - 500= 100. 33% of 100 is 33. Thus the total tax is 125 + 33 = 158.

One more example is a gross of 720. Again this will be taxed as 25% of the first 500 which gives us 125, and 33% of the remainder which is 720-500 = 220. 33% of 220 is 72.60. Thus the total tax will be 125 + 72.60 = 197.60.

Now let us see how we will implement this in our JavaScript programme.

Go to top

The if..else Construct

Looking at Listing 1 below we see that it is similar to the previous application we looked at in 'A basic JavaScript Program' Lines 1 to 5 and lines 15 to 19 are identical to their predecessors, but lines 6 to 14 are new.

These are the lines that control whether we calculate tax on a low flat rate of 25% or at the higher rate 125 plus 33% of the amount above 500. As they are the only new lines in the application we shall concentrate only on them.

Listing 1
                        function calculatePay()
                        {
                            const sngHours = parseFloat(document.getElementById("Hours").value);
                            const curRate = parseFloat(document.getElementById("Rate").value);
                            const curGross = sngHours * curRate;
                            let curTax;
                            if (curGross < 500)
                            {
                                curTax = curGross * 0.25;
                            }
                            else
                            {
                                curTax = 125 + (curGross - 500) * 0.33;
                            }
                            const curNet = curGross - curTax;
                            document.getElementById("Gross").value = curGross.toFixed(2);
                            document.getElementById("Tax").value = curTax.toFixed(2);
                            document.getElementById("Net").value = curNet.toFixed(2);
                        }
                    

Line 5 above calculates the gross and stores the value in the variable curGross, just like it did in the previous example. In line 6 we initialise the variable curTax. Here we use the keyword let. The reason for this is that within the program the curTax variable can have any one of two values, depending on the value of curGross

Lines 7 to 14 are the new lines that control the calculation of the tax. This is done using the if..else construct. This construct is used to make decisions based on a condition. In our case the condition is whether the gross is less than 500. If it is then the tax is calculated at 25% of the gross. If it is not then the tax is calculated as 125 plus 33% of the gross above 500.

The construct starts with the keyword if, which is followed by the condition inside brackets, i.e. (curGross < 500. This condition can be either true or false. As an example if curGross has a value of 400 then the condition is true, whereas if curGross has a value of 700 then the condition is false.

If the condition is true, i.e. if curGross has a value of 400, then the body of the if is executed, which only consists of line 9. In this line tax is calculated as 25% of the gross. Once the line has finished execution the else at line 11 and the body of the else at line 13 are skipped and control jumps to line 15 where the net is calculated.

On the other hand if the value of curGross is 700 then the condition at line 7 is false. In this case the body of the if is skipped and control passes down to line 13, i.e. the body of the else, where tax is calculated as 125 + 33 % of 200, giving 191.

In our example the body of the if and the body of the else had only one command line each. How would we deal with it if both bodies had more than one command line. The diagram below shows how this would be handled.

command 1

if(condition)

{

command 2

command 3

}

else

{

command 4

command 5

}

command 6

As can be seen the group of commands in the body of the if are enclosed between curly brackets. Thus if the condition is true the body of the if is executed, i.e. command 2 and command 3. Then program control skips to command 6.

If the condition is false then command 2 and command 3 are skipped and command 4 and command 5 are executed. Program flow then flows naturally to command 6.

Simple Form
Fig 1: a sample output from our JavaScript code.
Go to top

The switch Construct

The if..else construct is fine when we have a yes/no situation, or in other words when we have only two choices. Although it can handle multiple choices, its structure can become very awkward. In order to avoid this we use the more elegant switch construct.

In order to explore this new construct we shall extend and alter our payroll application to include the calculation of superannuation. As well as entering the values of the hours worked and the hourly rate, the user will also enter a superannuation code. This code determines the percentage of the gross that will be deducted as superannuation. The table below shows the relationship between the code and the percentage.

CodePercentage
00
15
210
315
420

In order to accommodate this change in the payroll processing, some changes will need to be made to both the form layout and the JavaScript code.

Two more fields will need to be added to the form: one for entering the superannuation code and another for displaying the superannuation amount.

For the JavaScript code a new technique must be employed to determine the correct percentage to apply when calculating the superannuation.

There is no change in the layout of the forms and therefore there is no need to alter the CSS file.

The HTML markup for the form is shown below. The additional code is shown bold.

Listing 2
                        <!doctype html>
                        <html lang="en">
                            <head>
                                <link href="Forms.css" rel="stylesheet" type="text/css">
                                <script src="Switch.js" type='text/javascript'></script>
                            </head>
                            <body>
                                <main>
                                   <a id="TopOfMain"></a>
                                    <form>
                                        <legend>All fields marked with * are required<br>Fields with shadowed backgrounds are in error</legend>
                                        <fieldset>
                                            <p>
                                                <label for="Hours">Hours Worked *</label><input type="number" id="Hours" name="Hours" min = "10" max="60" value="40" required>
                                            </p>
                                            <p>
                                                <label for="Rate">Hourly Rate *</label><input type="number" id="Rate" name="Rate" min="20" max="80" value="30" required >
                                            </p>
                                            <p>
                                                <label for="SRate">Super Rate *</label><input type="number" id="SRate" name="SRate" min="0" max="4" value="1" required >
                                            </p>
                                            <p>
                                                <label for="Gross">Gross</label><input type="text" name="Gross" id="Gross" disabled  >
                                            </p>
                                            <p>
                                                <label for="Tax">Tax</label><input type="text" name="Tax" id="Tax" disabled >
                                            </p>
                                            <p>
                                                <label for="Super">Super Amt</label><input type="text" name="Super" id="Super" disabled >
                                            </p>
                                            <p>
                                                <label for="Net">Net</label><input type="text" name="Net" id="Net" disabled >
                                            </p>
                                        </fieldset>
                                        <input type="button" value="Calculate Pay"  onclick="calculatePay()">
                                    </form>
                                </main>
                            </body>
                        </html>
                    

The change in the form itself is fairly minor. We need to add two label/input fields at lines 20 and 29. Our first pair is for entering the superannuation rate and the other is for displaying the amount that is to be contributed towards superannuation.

The biggest change is to the JavaScript code shown below in Listing 3. It is three times the length of its predecessor in Listing 1 above.

Listing 3
                        const calculatePay = () => {
                            const sngHours = parseFloat(document.getElementById("Hours").value);
                            const curRate = parseFloat(document.getElementById("Rate").value);
                            const intSuperCode = document.getElementById("SRate").value;
                            let sngSuperRate;
                            let curTax;
                            switch (intSuperCode) {
                                case '0':
                                    sngSuperRate = 0;
                                    break;
                                case '1':
                                    sngSuperRate = 0.05;
                                    break;
                                case '2':
                                    sngSuperRate = 0.1;
                                    break;
                                case '3':
                                    sngSuperRate = 0.15;
                                    break;
                                case '4':
                                    sngSuperRate = 0.2;
                                    break;
                                default:
                                    sngSuperRate = -1;
                            }
                            if (sngSuperRate === -1) {
                                alert("Super code must be an integer in the range 0 - 4");
                            } else {
                                const curGross = sngHours * curRate;
                                if (curGross < 500) {
                                    curTax = curGross * 0.25;
                                } else {
                                    curTax = 125 + (curGross - 500) * 0.33;
                                }
                                const curSuper = curGross * sngSuperRate;
                                const curNet = curGross - curTax - curSuper;
                                document.getElementById("Gross").value = curGross.toFixed(2);
                                document.getElementById("Tax").value = curTax.toFixed(2);
                                document.getElementById("Super").value = curSuper.toFixed(2);
                                document.getElementById("Net").value = curNet.toFixed(2);
                            }
                        }
                    

The calculatePay function begins by defining several variables. First, it retrieves the user’s input for the number of hours worked sngHours and the hourly rate curRate. These inputs are fetched using document.getElementById to access the DOM elements with IDs Hours and Rate, respectively. Both values are converted into floating-point numbers using parseFloat, as these inputs are expected to be numerical.

Next, the code retrieves a “super code” intSuperCode from another DOM element with the ID SRate. This code determines the superannuation rate applied to the gross pay.

The variable sngSuperRate is then initialized to hold the superannuation rate, while curTax is reserved for the tax calculation later.

The program uses a switch statement to assign a superannuation rate sngSuperRate based on the value of intSuperCode. Each case corresponds to a specific super code:

After the switch block, the program checks if sngSuperRate is -1. If so, it alerts the user with a message explaining that the super code must be an integer between 0 and 4, and exits further processing.

If the super code is valid, the program calculates the gross pay curGross by multiplying the number of hours worked sngHours by the hourly rate curRate.

Next, the tax curTax is computed based on the gross pay. A conditional structure applies:

The superannuation amount curSuper is then calculated by multiplying the gross pay by the superannuation rate sngSuperRate.

The net pay curNet is determined by subtracting the tax and superannuation from the gross pay.

Finally, the program updates the values of DOM elements with IDs Gross, Tax, Super, and Net to display the calculated gross pay, tax, superannuation, and net pay, respectively. Each value is formatted to two decimal places using the toFixed method.

Below is a sample output from the piece of code.

Go to top

Summary

Decisions are an integral part of programming. They allow us to control the flow of a program based on specific conditions. The if..else construct is used to make binary decisions, while the switch construct is more suitable for multiple choices. Both constructs are essential tools for creating dynamic and responsive applications.

The uploaded file provides an educational guide on using decision-making constructs in JavaScript programming. It begins by outlining the learning objectives, emphasizing the ability to make binary decisions with the "if..else" construct and manage multiple choices with the "switch" construct. These constructs are foundational to developing logical and functional programs in JavaScript.

The introduction discusses the significance of decision-making in everyday life and programming. It uses relatable examples, such as deciding whether to go to town or study, to illustrate the concept. The narrative transitions into programming-specific scenarios, showcasing how decisions influence tasks like tax calculations. A detailed example of a payroll application demonstrates the step-by-step process of determining tax based on gross income, with conditions for different tax rates.

The file delves into the "if..else" construct, highlighting its use in situations requiring binary decisions. It provides annotated code snippets and a comprehensive explanation of how the program calculates tax for gross income below or above a specific threshold. It also explains the importance of using the "let" keyword for declaring variables with changing values.

In scenarios requiring more than two choices, the file introduces the "switch" construct as an elegant alternative to "if..else." An example is provided where a payroll application calculates superannuation contributions based on codes representing different percentages. A corresponding table links the codes to their respective percentages, and a JavaScript implementation showcases how the "switch" construct simplifies the decision-making process.

The guide also addresses error handling, illustrating how invalid inputs (e.g., incorrect superannuation codes) prompt user alerts. It emphasizes best practices in structuring conditional statements to improve code clarity and maintainability. Additionally, the program dynamically updates the calculated values for gross income, tax, superannuation, and net income in the user interface, leveraging DOM manipulation techniques.

Throughout the file, various examples of JavaScript functions, DOM access methods like "document.getElementById," and techniques such as the "toFixed" method for formatting numerical outputs are presented. These examples are accompanied by descriptions that clarify their application in real-world programming scenarios.

The document concludes with a focus on practical outputs, demonstrating how the constructs can be applied to create interactive and responsive applications. The combination of theoretical explanations, practical examples, and visually annotated code makes it a comprehensive resource for learning JavaScript decision-making constructs.

Go to top

Revision

Multiple choice

Fill in the blanks

Go to top

Assignment

Assignment Title: Sales Invoice Calculator

Objective: To create an interactive JavaScript application for a small business to calculate the total cost of items sold, including GST and discounts.

Instructions:

Deliverables:

Grading Criteria:

Extension Idea for Advanced Students:

Go to top