
VBScript solution to Event 8 in the 2008 Winter Scripting Games.
Solutions are also available for Windows PowerShell and Perl.
In this event you were required to do something a little different. Rather than creating a script in a VBScript file, you needed to write VBScript in an HTML Application (HTA). Not only did you need to learn something about creating an HTA, but you also needed to learn how to generate random numbers. Here’s the HTA we came up with to solve this event:
<head>
<title>Random Guess</title>
<HTA:APPLICATION
APPLICATIONNAME="Random Guess"
SCROLL="yes"
SINGLEINSTANCE="yes"
>
</head>
<script language="VBScript">
Dim intRnd
Dim iguesses
iguesses = 1
Sub window_onload
Randomize
intRnd = Int((50 * Rnd) + 1)
End Sub
Sub Guess
iguess = CInt(txtguess.value)
If iguess = intRnd Then
MsgBox "Random: " & intRnd & vbCrLf & "Total Guesses: " & iguesses
window.close
ElseIf iguess < intRnd Then
iguesses = iguesses + 1
MsgBox "Too Low"
Else
iguesses = iguesses + 1
MsgBox "Too High"
End If
End Sub
</script>
<body>
Enter a number between 1 and 50:
<input type="text" name="txtGuess" size="3">
<p>
<input id=1 class="button" type="button" name="Guess"
value="Guess" style="height:30px; width=45px" onClick="Guess">
</body>
An HTA can be broken down into three sections: the header, the script, and the body. We’ll take a quick look at the header first:
<head>
<title>Random Guess</title>
<HTA:APPLICATION
APPLICATIONNAME="Random Guess"
SCROLL="yes"
SINGLEINSTANCE="yes"
>
</head>
Here we’ve simply inserted some fields within an HTML <head> tag. We’ve given the HTA a title (enclosed in <title> tags), Random Guess; and we’ve defined several fields identifying this as an HTA rather than an HTML file.
We’re going to skip the script section for a moment and look at the body section:
<body>
Enter a number between 1 and 50:
<input type="text" name="txtGuess" size="3">
<p>
<input id=1 class="button" type="button" name="Guess"
value="Guess" style="height:30px; width=45px" onClick="Guess">
</body>
We start by entering a line of text. Because we simply typed this text inside the body tags without any options, the text will appear in the HTA window as-is with no special formatting. The text we display instructs the user on what to do; in this case enter a number between 1 and 50:
Enter a number between 1 and 50:
Now we need to give the user a place to enter that number. We’ve provided them with a text box for that purpose:
<input type="text" name="txtGuess" size="3">
A text box is defined by using the <input> tag with a type equal to “text.” We’ve also given our text box a name, txtGuess, so we can reference it within our script code. In addition, we gave the box a size of 3. This could have been 2; the numbers 1 through 50 will never take more than two characters. But we decided to give a little more room just because. You could have made this box any size you want.
After putting in a paragraph tag (<p>) to separate the fields, we added a button for the user to press that will submit their guess:
<input id=1 class="button" type="button" name="Guess"
value="Guess" style="height:30px; width=45px" onClick="Guess">
Like the text box, the button is also defined with the input tag, but instead of a type of “text” we set the type to “button”. (Makes sense, right?) The label that is displayed on the button is “Guess”, which we set with the name property. The class is set to “button” to specify that we want the button to look like a button, and we set the value to “Guess”. We also defined a height and width, in pixels (that’s what the px stands for), by using the style property. Finally, we set the onClick property to “Guess”. The value assigned to the onClick property is the name of the subroutine that will run when the button is clicked.
Now that we have all our HTML elements defined, let’s take a look at the script section of our HTA:
<script language="VBScript">
Dim intRnd
Dim iguesses
iguesses = 1
Sub window_onload
Randomize
intRnd = Int((50 * Rnd) + 1)
End Sub
Sub Guess
iguess = CInt(txtguess.value)
If iguess = intRnd Then
MsgBox "Random: " & intRnd & vbCrLf & "Total Guesses: " & iguesses
window.close
ElseIf iguess < intRnd Then
iguesses = iguesses + 1
MsgBox "Too Low"
Else
iguesses = iguesses + 1
MsgBox "Too High"
End If
End Sub
</script>
We start by defining a couple of variables:
Dim intRnd Dim iguesses
By defining these variables at the beginning of our script section, outside of any subroutines, these variables will be available and will retain their values throughout all subroutines. That means that once you set one of these variables you can change its value anywhere inside the script tags and the value will be retained until it’s been changed somewhere else in the script. or the HTA is shut down. The variables we’ve defined will keep track of the random number we generate (intRnd) and the number of tries it takes to guess that number (iguesses). We initialize the latter to 1 to start:
iguesses = 1
Next comes the subroutine window_onload:
Sub window_onload
Randomize
intRnd = Int((50 * Rnd) + 1)
End Sub
The name of this subroutine isn’t something we just made up. Including a subroutine named window_onload in your HTA tells the HTA that it needs to run that subroutine as soon as the HTA is opened. Inside this subroutine we set the random number with these two lines of code:
Randomize intRnd = Int((50 * Rnd) + 1)
The Randomize method sets the seed for our random-number generator (based on the system date and time). The next line uses the Rnd function to randomly select a number – in this case between 1 (that’s what the +1 is) and 50. (Hopefully you found the answer to this part pretty easily, since we explained it in one of our Scripting Games Tips.)
Now that we have our random number, we simply wait for the user to enter a number into the text box and press the Guess button. As soon as he or she presses that button we run the Guess subroutine:
Sub Guess
iguess = CInt(txtguess.value)
If iguess = intRnd Then
MsgBox "Random: " & intRnd & vbCrLf & "Total Guesses: " & iguesses
window.close
ElseIf iguess < intRnd Then
iguesses = iguesses + 1
MsgBox "Too Low"
Else
iguesses = iguesses + 1
MsgBox "Too High"
End If
End Sub
By default, values entered into a text box are treated like strings. Because we’re working with numbers and will be doing numerical comparisons on the value entered, the first thing we do is call the CInt function to explicitly turn the value of the txtguess text box into an integer:
iguess = CInt(txtguess.value)
Next we need to compare the number that was guessed to the random number:
If iguess = intRnd Then
According to the event instruction, if the two values are the same we need to bring up a message box that displays the value of the random number and the total number of tries it took to correctly guess that number:
MsgBox "Random: " & intRnd & vbCrLf & "Total Guesses: " & iguesses
As you can see, we use the MsgBox function to display the message box, passing it a string with the random number and the number of guesses. At this point the game is over, so we call the windows.close method to shut down the HTA:
window.close
But what happens if the number entered by the user isn’t the same as the random number? Well, in that case we need to display a message box telling them whether they guessed too high or too low so they can try again. First we check to see if the guess was lower than (less than) the random number:
ElseIf iguess < intRnd Then
If it is, we first increment the number of guesses the user has tried, then we display the message box telling them their most recent guess was too low:
iguesses = iguesses + 1 MsgBox "Too Low"
If the guess wasn’t the same as the random number, and it wasn’t less than the random number, then it must have been greater than the random number (too high). That brings us to the Else statement:
Else
iguesses = iguesses + 1
MsgBox "Too High"
If they guess was too low we again need to increment the variable that’s keeping track of our number of guesses, then display a message box stating that the guess was too high.
And that’s it. The HTA will display “Too High” or “Too Low” as long as the user continues to enter numbers and click the Guess button. When the user guesses correctly a message box will display that fact and the HTA will close.
Now, if that’s not the most fun you’ve had playing a game in a long time, well, you obviously have no concept of how to actually have fun.